dbee-active_record 1.0.0.pre.alpha

Sign up to get free protection for your applications and to get access to all the features.
Files changed (39) hide show
  1. checksums.yaml +7 -0
  2. data/.editorconfig +8 -0
  3. data/.gitignore +7 -0
  4. data/.rubocop.yml +27 -0
  5. data/.ruby-version +1 -0
  6. data/.travis.yml +30 -0
  7. data/CHANGELOG.md +7 -0
  8. data/CODE_OF_CONDUCT.md +74 -0
  9. data/Gemfile +5 -0
  10. data/Guardfile +16 -0
  11. data/LICENSE +7 -0
  12. data/README.md +75 -0
  13. data/Rakefile +15 -0
  14. data/bin/console +18 -0
  15. data/dbee-active_record.gemspec +36 -0
  16. data/lib/dbee/providers/active_record_provider/expression_builder/constraint_maker.rb +50 -0
  17. data/lib/dbee/providers/active_record_provider/expression_builder/order_maker.rb +23 -0
  18. data/lib/dbee/providers/active_record_provider/expression_builder/select_maker.rb +31 -0
  19. data/lib/dbee/providers/active_record_provider/expression_builder/where_maker.rb +54 -0
  20. data/lib/dbee/providers/active_record_provider/expression_builder.rb +169 -0
  21. data/lib/dbee/providers/active_record_provider/obfuscated_alias_maker.rb +40 -0
  22. data/lib/dbee/providers/active_record_provider/safe_alias_maker.rb +21 -0
  23. data/lib/dbee/providers/active_record_provider/version.rb +16 -0
  24. data/lib/dbee/providers/active_record_provider.rb +51 -0
  25. data/spec/config/database.yaml.ci +9 -0
  26. data/spec/db_helper.rb +56 -0
  27. data/spec/dbee/providers/active_record_provider_spec.rb +79 -0
  28. data/spec/fixtures/active_record_snapshots/five_table_query.yaml +77 -0
  29. data/spec/fixtures/active_record_snapshots/multiple_same_table_query_with_static_constraints.yaml +104 -0
  30. data/spec/fixtures/active_record_snapshots/one_table_query.yaml +26 -0
  31. data/spec/fixtures/active_record_snapshots/one_table_query_with_ascending_sort.yaml +31 -0
  32. data/spec/fixtures/active_record_snapshots/one_table_query_with_descending_sort.yaml +32 -0
  33. data/spec/fixtures/active_record_snapshots/one_table_query_with_filters.yaml +170 -0
  34. data/spec/fixtures/active_record_snapshots/one_table_query_with_limit.yaml +30 -0
  35. data/spec/fixtures/active_record_snapshots/one_table_query_with_multiple_sorts.yaml +33 -0
  36. data/spec/fixtures/active_record_snapshots/two_table_query.yaml +44 -0
  37. data/spec/fixtures/models.yaml +66 -0
  38. data/spec/spec_helper.rb +52 -0
  39. metadata +256 -0
@@ -0,0 +1,40 @@
1
+ # frozen_string_literal: true
2
+
3
+ #
4
+ # Copyright (c) 2019-present, Blue Marble Payroll, LLC
5
+ #
6
+ # This source code is licensed under the MIT license found in the
7
+ # LICENSE file in the root directory of this source tree.
8
+ #
9
+
10
+ module Dbee
11
+ module Providers
12
+ class ActiveRecordProvider
13
+ # Derives new alias names and keeps count of ones already generated in order to avoid
14
+ # collision.
15
+ class ObfuscatedAliasMaker
16
+ attr_reader :prefix
17
+
18
+ def initialize(prefix = '')
19
+ @counter = -1
20
+ @prefix = prefix
21
+ end
22
+
23
+ def make(_name)
24
+ increment
25
+ current
26
+ end
27
+
28
+ private
29
+
30
+ def current
31
+ "#{prefix}#{@counter}"
32
+ end
33
+
34
+ def increment
35
+ @counter += 1
36
+ end
37
+ end
38
+ end
39
+ end
40
+ end
@@ -0,0 +1,21 @@
1
+ # frozen_string_literal: true
2
+
3
+ #
4
+ # Copyright (c) 2019-present, Blue Marble Payroll, LLC
5
+ #
6
+ # This source code is licensed under the MIT license found in the
7
+ # LICENSE file in the root directory of this source tree.
8
+ #
9
+
10
+ module Dbee
11
+ module Providers
12
+ class ActiveRecordProvider
13
+ # This class can be used when readable alias names are expected.
14
+ class SafeAliasMaker
15
+ def make(name)
16
+ name.to_s.tr('.', '_')
17
+ end
18
+ end
19
+ end
20
+ end
21
+ end
@@ -0,0 +1,16 @@
1
+ # frozen_string_literal: true
2
+
3
+ #
4
+ # Copyright (c) 2019-present, Blue Marble Payroll, LLC
5
+ #
6
+ # This source code is licensed under the MIT license found in the
7
+ # LICENSE file in the root directory of this source tree.
8
+ #
9
+
10
+ module Dbee
11
+ module Providers
12
+ class ActiveRecordProvider
13
+ VERSION = '1.0.0-alpha'
14
+ end
15
+ end
16
+ end
@@ -0,0 +1,51 @@
1
+ # frozen_string_literal: true
2
+
3
+ #
4
+ # Copyright (c) 2019-present, Blue Marble Payroll, LLC
5
+ #
6
+ # This source code is licensed under the MIT license found in the
7
+ # LICENSE file in the root directory of this source tree.
8
+ #
9
+
10
+ require 'dbee'
11
+ require 'active_record'
12
+
13
+ require_relative 'active_record_provider/expression_builder'
14
+ require_relative 'active_record_provider/obfuscated_alias_maker'
15
+ require_relative 'active_record_provider/safe_alias_maker'
16
+
17
+ module Dbee
18
+ module Providers
19
+ # Provider which leverages ActiveRecord and Arel for generating SQL.
20
+ class ActiveRecordProvider
21
+ DEFAULT_TABLE_PREFIX = 't'
22
+ DEFAULT_COLUMN_PREFIX = 'c'
23
+
24
+ attr_reader :readable, :table_alias_maker, :column_alias_maker
25
+
26
+ def initialize(
27
+ readable: true,
28
+ table_prefix: DEFAULT_TABLE_PREFIX,
29
+ column_prefix: DEFAULT_COLUMN_PREFIX
30
+ )
31
+ @readable = readable
32
+ @table_alias_maker = alias_maker(table_prefix)
33
+ @column_alias_maker = alias_maker(column_prefix)
34
+ end
35
+
36
+ def sql(model, query)
37
+ ExpressionBuilder.new(
38
+ model,
39
+ table_alias_maker,
40
+ column_alias_maker
41
+ ).add(query).to_sql
42
+ end
43
+
44
+ private
45
+
46
+ def alias_maker(prefix)
47
+ readable ? SafeAliasMaker.new : ObfuscatedAliasMaker.new(prefix)
48
+ end
49
+ end
50
+ end
51
+ end
@@ -0,0 +1,9 @@
1
+ sqlite:
2
+ adapter: sqlite3
3
+ database: ':memory:'
4
+ mysql:
5
+ adapter: mysql2
6
+ database: dbee_test
7
+ username: root
8
+ host: 127.0.0.1
9
+ port: 3306
data/spec/db_helper.rb ADDED
@@ -0,0 +1,56 @@
1
+ # frozen_string_literal: true
2
+
3
+ #
4
+ # Copyright (c) 2018-present, Blue Marble Payroll, LLC
5
+ #
6
+ # This source code is licensed under the MIT license found in the
7
+ # LICENSE file in the root directory of this source tree.
8
+ #
9
+
10
+ # Enable logging using something like:
11
+ # ActiveRecord::Base.logger = Logger.new(STDERR)
12
+
13
+ def connect_to_db(name)
14
+ config = yaml_file_read('spec', 'config', 'database.yaml')[name.to_s]
15
+ ActiveRecord::Base.establish_connection(config)
16
+ end
17
+
18
+ def load_schema
19
+ ActiveRecord::Schema.define do
20
+ create_table :theaters do |t|
21
+ t.column :name, :string
22
+ t.column :partition, :string
23
+ t.column :active, :boolean
24
+ t.column :inspected, :boolean
25
+ t.timestamps
26
+ end
27
+
28
+ create_table :members do |t|
29
+ t.column :tid, :integer
30
+ t.column :account_number, :string
31
+ t.column :partition, :string
32
+ t.timestamps
33
+ end
34
+
35
+ create_table :demographics do |t|
36
+ t.column :member_id, :integer
37
+ t.column :name, :string
38
+ t.timestamps
39
+ end
40
+
41
+ create_table :phone_numbers do |t|
42
+ t.column :demographic_id, :integer
43
+ t.column :phone_type, :string
44
+ t.column :phone_number, :string
45
+ t.timestamps
46
+ end
47
+
48
+ create_table :movies do |t|
49
+ t.column :member_id, :integer
50
+ t.column :name, :string
51
+ t.column :genre, :string
52
+ t.column :favorite, :boolean, default: false, null: false
53
+ t.timestamps
54
+ end
55
+ end
56
+ end
@@ -0,0 +1,79 @@
1
+ # frozen_string_literal: true
2
+
3
+ #
4
+ # Copyright (c) 2019-present, Blue Marble Payroll, LLC
5
+ #
6
+ # This source code is licensed under the MIT license found in the
7
+ # LICENSE file in the root directory of this source tree.
8
+ #
9
+
10
+ require 'spec_helper'
11
+ require 'db_helper'
12
+
13
+ describe Dbee::Providers::ActiveRecordProvider do
14
+ let(:models) { yaml_fixture('models.yaml') }
15
+
16
+ describe 'Snapshot' do
17
+ context 'Generating SQL' do
18
+ %w[sqlite mysql].each do |dbms|
19
+ context dbms do
20
+ before(:all) do
21
+ connect_to_db(dbms)
22
+ end
23
+
24
+ { readable: true, not_readable: false }.each_pair do |type, readable|
25
+ context type.to_s do
26
+ let(:key) { "#{dbms}_#{type}" }
27
+
28
+ yaml_fixture_files('active_record_snapshots').each_pair do |filename, snapshot|
29
+ specify File.basename(filename) do
30
+ model_name = snapshot['model_name']
31
+ query = Dbee::Query.make(snapshot['query'])
32
+ model = Dbee::Model.make(models[model_name])
33
+ expected_sql = snapshot[key].to_s.chomp.tr("\n", ' ')
34
+ actual_sql = described_class.new(readable: readable).sql(model, query)
35
+
36
+ error_msg = <<~ERROR_MSG
37
+ Expected: #{expected_sql}
38
+ Actual: #{actual_sql}
39
+ ERROR_MSG
40
+
41
+ expect(actual_sql).to eq(expected_sql), error_msg
42
+ end
43
+ end
44
+ end
45
+ end
46
+ end
47
+ end
48
+ end
49
+
50
+ context 'Executing SQL' do
51
+ %w[sqlite].each do |dbms|
52
+ context dbms do
53
+ before(:all) do
54
+ connect_to_db(dbms)
55
+ load_schema
56
+ end
57
+
58
+ { readable: true, not_readable: false }.each_pair do |type, readable|
59
+ context type.to_s do
60
+ let(:key) { "#{dbms}_#{type}" }
61
+
62
+ yaml_fixture_files('active_record_snapshots').each_pair do |filename, snapshot|
63
+ specify File.basename(filename) do
64
+ model_name = snapshot['model_name']
65
+ query = Dbee::Query.make(snapshot['query'])
66
+ model = Dbee::Model.make(models[model_name])
67
+
68
+ sql = described_class.new(readable: readable).sql(model, query)
69
+
70
+ expect { ActiveRecord::Base.connection.execute(sql) }.to_not raise_error
71
+ end
72
+ end
73
+ end
74
+ end
75
+ end
76
+ end
77
+ end
78
+ end
79
+ end
@@ -0,0 +1,77 @@
1
+ model_name: Theaters, Members, and Movies
2
+ query:
3
+ fields:
4
+ - key_path: members.demos.phone_numbers.phone_number
5
+ display: PHONE NUMBER
6
+ - key_path: members.demos.name
7
+ - key_path: id
8
+ - key_path: name
9
+ - key_path: members.movies.id
10
+ - key_path: members.id
11
+ - key_path: members.account_number
12
+ - key_path: members.demos.phone_numbers.phone_type
13
+ - key_path: members.movies.name
14
+ sqlite_readable: |+
15
+ SELECT
16
+ "members_demos_phone_numbers"."phone_number" AS 'PHONE NUMBER',
17
+ "members_demos"."name" AS 'members_demos_name',
18
+ "theaters"."id" AS 'id',
19
+ "theaters"."name" AS 'name',
20
+ "members_movies"."id" AS 'members_movies_id',
21
+ "members"."id" AS 'members_id',
22
+ "members"."account_number" AS 'members_account_number',
23
+ "members_demos_phone_numbers"."phone_type" AS 'members_demos_phone_numbers_phone_type',
24
+ "members_movies"."name" AS 'members_movies_name'
25
+ FROM "theaters" "theaters"
26
+ LEFT OUTER JOIN "members" "members" ON "members"."tid" = "theaters"."id" AND "members"."partition" = "theaters"."partition"
27
+ LEFT OUTER JOIN "demographics" "members_demos" ON "members_demos"."member_id" = "members"."id"
28
+ LEFT OUTER JOIN "phone_numbers" "members_demos_phone_numbers" ON "members_demos_phone_numbers"."demographic_id" = "members_demos"."id"
29
+ LEFT OUTER JOIN "movies" "members_movies" ON "members_movies"."member_id" = "members"."id"
30
+ sqlite_not_readable: |+
31
+ SELECT
32
+ "t3"."phone_number" AS 'c0',
33
+ "t2"."name" AS 'c1',
34
+ "t0"."id" AS 'c2',
35
+ "t0"."name" AS 'c3',
36
+ "t4"."id" AS 'c4',
37
+ "t1"."id" AS 'c5',
38
+ "t1"."account_number" AS 'c6',
39
+ "t3"."phone_type" AS 'c7',
40
+ "t4"."name" AS 'c8'
41
+ FROM "theaters" "t0"
42
+ LEFT OUTER JOIN "members" "t1" ON "t1"."tid" = "t0"."id" AND "t1"."partition" = "t0"."partition"
43
+ LEFT OUTER JOIN "demographics" "t2" ON "t2"."member_id" = "t1"."id"
44
+ LEFT OUTER JOIN "phone_numbers" "t3" ON "t3"."demographic_id" = "t2"."id"
45
+ LEFT OUTER JOIN "movies" "t4" ON "t4"."member_id" = "t1"."id"
46
+ mysql_readable: |+
47
+ SELECT
48
+ `members_demos_phone_numbers`.`phone_number` AS 'PHONE NUMBER',
49
+ `members_demos`.`name` AS 'members_demos_name',
50
+ `theaters`.`id` AS 'id',
51
+ `theaters`.`name` AS 'name',
52
+ `members_movies`.`id` AS 'members_movies_id',
53
+ `members`.`id` AS 'members_id',
54
+ `members`.`account_number` AS 'members_account_number',
55
+ `members_demos_phone_numbers`.`phone_type` AS 'members_demos_phone_numbers_phone_type',
56
+ `members_movies`.`name` AS 'members_movies_name'
57
+ FROM `theaters` `theaters`
58
+ LEFT OUTER JOIN `members` `members` ON `members`.`tid` = `theaters`.`id` AND `members`.`partition` = `theaters`.`partition`
59
+ LEFT OUTER JOIN `demographics` `members_demos` ON `members_demos`.`member_id` = `members`.`id`
60
+ LEFT OUTER JOIN `phone_numbers` `members_demos_phone_numbers` ON `members_demos_phone_numbers`.`demographic_id` = `members_demos`.`id`
61
+ LEFT OUTER JOIN `movies` `members_movies` ON `members_movies`.`member_id` = `members`.`id`
62
+ mysql_not_readable: |+
63
+ SELECT
64
+ `t3`.`phone_number` AS 'c0',
65
+ `t2`.`name` AS 'c1',
66
+ `t0`.`id` AS 'c2',
67
+ `t0`.`name` AS 'c3',
68
+ `t4`.`id` AS 'c4',
69
+ `t1`.`id` AS 'c5',
70
+ `t1`.`account_number` AS 'c6',
71
+ `t3`.`phone_type` AS 'c7',
72
+ `t4`.`name` AS 'c8'
73
+ FROM `theaters` `t0`
74
+ LEFT OUTER JOIN `members` `t1` ON `t1`.`tid` = `t0`.`id` AND `t1`.`partition` = `t0`.`partition`
75
+ LEFT OUTER JOIN `demographics` `t2` ON `t2`.`member_id` = `t1`.`id`
76
+ LEFT OUTER JOIN `phone_numbers` `t3` ON `t3`.`demographic_id` = `t2`.`id`
77
+ LEFT OUTER JOIN `movies` `t4` ON `t4`.`member_id` = `t1`.`id`
@@ -0,0 +1,104 @@
1
+ model_name: Theaters, Members, and Movies
2
+ query:
3
+ fields:
4
+ - key_path: id
5
+ - key_path: name
6
+ - key_path: members.id
7
+ - key_path: members.account_number
8
+ - key_path: members.movies.id
9
+ - key_path: members.movies.name
10
+ display: 'Movie Name'
11
+ - key_path: members.movies.genre
12
+ - key_path: members.favorite_comic_movies.id
13
+ - key_path: members.favorite_comic_movies.name
14
+ display: 'Favorite Comic Movie Name'
15
+ - key_path: members.favorite_comic_movies.genre
16
+ - key_path: members.favorite_mystery_movies.id
17
+ - key_path: members.favorite_mystery_movies.name
18
+ display: 'Favorite Mystery Movie Name'
19
+ - key_path: members.favorite_mystery_movies.genre
20
+ limit: 12
21
+ sqlite_readable: |+
22
+ SELECT
23
+ "theaters"."id" AS 'id',
24
+ "theaters"."name" AS 'name',
25
+ "members"."id" AS 'members_id',
26
+ "members"."account_number" AS 'members_account_number',
27
+ "members_movies"."id" AS 'members_movies_id',
28
+ "members_movies"."name" AS 'Movie Name',
29
+ "members_movies"."genre" AS 'members_movies_genre',
30
+ "members_favorite_comic_movies"."id" AS 'members_favorite_comic_movies_id',
31
+ "members_favorite_comic_movies"."name" AS 'Favorite Comic Movie Name',
32
+ "members_favorite_comic_movies"."genre" AS 'members_favorite_comic_movies_genre',
33
+ "members_favorite_mystery_movies"."id" AS 'members_favorite_mystery_movies_id',
34
+ "members_favorite_mystery_movies"."name" AS 'Favorite Mystery Movie Name',
35
+ "members_favorite_mystery_movies"."genre" AS 'members_favorite_mystery_movies_genre'
36
+ FROM "theaters" "theaters"
37
+ LEFT OUTER JOIN "members" "members" ON "members"."tid" = "theaters"."id" AND "members"."partition" = "theaters"."partition"
38
+ LEFT OUTER JOIN "movies" "members_movies" ON "members_movies"."member_id" = "members"."id"
39
+ LEFT OUTER JOIN "movies" "members_favorite_comic_movies" ON "members_favorite_comic_movies"."member_id" = "members"."id" AND "members_favorite_comic_movies"."genre" = 'comic'
40
+ LEFT OUTER JOIN "movies" "members_favorite_mystery_movies" ON "members_favorite_mystery_movies"."member_id" = "members"."id" AND "members_favorite_mystery_movies"."genre" = 'mystery'
41
+ LIMIT 12
42
+ sqlite_not_readable: |+
43
+ SELECT
44
+ "t0"."id" AS 'c0',
45
+ "t0"."name" AS 'c1',
46
+ "t1"."id" AS 'c2',
47
+ "t1"."account_number" AS 'c3',
48
+ "t2"."id" AS 'c4',
49
+ "t2"."name" AS 'c5',
50
+ "t2"."genre" AS 'c6',
51
+ "t3"."id" AS 'c7',
52
+ "t3"."name" AS 'c8',
53
+ "t3"."genre" AS 'c9',
54
+ "t4"."id" AS 'c10',
55
+ "t4"."name" AS 'c11',
56
+ "t4"."genre" AS 'c12'
57
+ FROM "theaters" "t0"
58
+ LEFT OUTER JOIN "members" "t1" ON "t1"."tid" = "t0"."id" AND "t1"."partition" = "t0"."partition"
59
+ LEFT OUTER JOIN "movies" "t2" ON "t2"."member_id" = "t1"."id"
60
+ LEFT OUTER JOIN "movies" "t3" ON "t3"."member_id" = "t1"."id" AND "t3"."genre" = 'comic'
61
+ LEFT OUTER JOIN "movies" "t4" ON "t4"."member_id" = "t1"."id" AND "t4"."genre" = 'mystery'
62
+ LIMIT 12
63
+ mysql_readable: |+
64
+ SELECT
65
+ `theaters`.`id` AS 'id',
66
+ `theaters`.`name` AS 'name',
67
+ `members`.`id` AS 'members_id',
68
+ `members`.`account_number` AS 'members_account_number',
69
+ `members_movies`.`id` AS 'members_movies_id',
70
+ `members_movies`.`name` AS 'Movie Name',
71
+ `members_movies`.`genre` AS 'members_movies_genre',
72
+ `members_favorite_comic_movies`.`id` AS 'members_favorite_comic_movies_id',
73
+ `members_favorite_comic_movies`.`name` AS 'Favorite Comic Movie Name',
74
+ `members_favorite_comic_movies`.`genre` AS 'members_favorite_comic_movies_genre',
75
+ `members_favorite_mystery_movies`.`id` AS 'members_favorite_mystery_movies_id',
76
+ `members_favorite_mystery_movies`.`name` AS 'Favorite Mystery Movie Name',
77
+ `members_favorite_mystery_movies`.`genre` AS 'members_favorite_mystery_movies_genre'
78
+ FROM `theaters` `theaters`
79
+ LEFT OUTER JOIN `members` `members` ON `members`.`tid` = `theaters`.`id` AND `members`.`partition` = `theaters`.`partition`
80
+ LEFT OUTER JOIN `movies` `members_movies` ON `members_movies`.`member_id` = `members`.`id`
81
+ LEFT OUTER JOIN `movies` `members_favorite_comic_movies` ON `members_favorite_comic_movies`.`member_id` = `members`.`id` AND `members_favorite_comic_movies`.`genre` = 'comic'
82
+ LEFT OUTER JOIN `movies` `members_favorite_mystery_movies` ON `members_favorite_mystery_movies`.`member_id` = `members`.`id` AND `members_favorite_mystery_movies`.`genre` = 'mystery'
83
+ LIMIT 12
84
+ mysql_not_readable: |+
85
+ SELECT
86
+ `t0`.`id` AS 'c0',
87
+ `t0`.`name` AS 'c1',
88
+ `t1`.`id` AS 'c2',
89
+ `t1`.`account_number` AS 'c3',
90
+ `t2`.`id` AS 'c4',
91
+ `t2`.`name` AS 'c5',
92
+ `t2`.`genre` AS 'c6',
93
+ `t3`.`id` AS 'c7',
94
+ `t3`.`name` AS 'c8',
95
+ `t3`.`genre` AS 'c9',
96
+ `t4`.`id` AS 'c10',
97
+ `t4`.`name` AS 'c11',
98
+ `t4`.`genre` AS 'c12'
99
+ FROM `theaters` `t0`
100
+ LEFT OUTER JOIN `members` `t1` ON `t1`.`tid` = `t0`.`id` AND `t1`.`partition` = `t0`.`partition`
101
+ LEFT OUTER JOIN `movies` `t2` ON `t2`.`member_id` = `t1`.`id`
102
+ LEFT OUTER JOIN `movies` `t3` ON `t3`.`member_id` = `t1`.`id` AND `t3`.`genre` = 'comic'
103
+ LEFT OUTER JOIN `movies` `t4` ON `t4`.`member_id` = `t1`.`id` AND `t4`.`genre` = 'mystery'
104
+ LIMIT 12
@@ -0,0 +1,26 @@
1
+ model_name: Theaters, Members, and Movies
2
+ query:
3
+ fields:
4
+ - key_path: id
5
+ display: 'ID #'
6
+ - key_path: name
7
+ sqlite_not_readable: |+
8
+ SELECT
9
+ "t0"."id" AS 'c0',
10
+ "t0"."name" AS 'c1'
11
+ FROM "theaters" "t0"
12
+ sqlite_readable: |+
13
+ SELECT
14
+ "theaters"."id" AS 'ID #',
15
+ "theaters"."name" AS 'name'
16
+ FROM "theaters" "theaters"
17
+ mysql_not_readable: |+
18
+ SELECT
19
+ `t0`.`id` AS 'c0',
20
+ `t0`.`name` AS 'c1'
21
+ FROM `theaters` `t0`
22
+ mysql_readable: |+
23
+ SELECT
24
+ `theaters`.`id` AS 'ID #',
25
+ `theaters`.`name` AS 'name'
26
+ FROM `theaters` `theaters`
@@ -0,0 +1,31 @@
1
+ model_name: Theaters, Members, and Movies
2
+ query:
3
+ fields:
4
+ - key_path: id
5
+ - key_path: name
6
+ sorters:
7
+ - key_path: created_at
8
+ sqlite_readable: |+
9
+ SELECT
10
+ "theaters"."id" AS 'id',
11
+ "theaters"."name" AS 'name'
12
+ FROM "theaters" "theaters"
13
+ ORDER BY "theaters"."created_at"
14
+ sqlite_not_readable: |+
15
+ SELECT
16
+ "t0"."id" AS 'c0',
17
+ "t0"."name" AS 'c1'
18
+ FROM "theaters" "t0"
19
+ ORDER BY "t0"."created_at"
20
+ mysql_readable: |+
21
+ SELECT
22
+ `theaters`.`id` AS 'id',
23
+ `theaters`.`name` AS 'name'
24
+ FROM `theaters` `theaters`
25
+ ORDER BY `theaters`.`created_at`
26
+ mysql_not_readable: |+
27
+ SELECT
28
+ `t0`.`id` AS 'c0',
29
+ `t0`.`name` AS 'c1'
30
+ FROM `theaters` `t0`
31
+ ORDER BY `t0`.`created_at`
@@ -0,0 +1,32 @@
1
+ model_name: Theaters, Members, and Movies
2
+ query:
3
+ fields:
4
+ - key_path: id
5
+ - key_path: name
6
+ sorters:
7
+ - key_path: created_at
8
+ direction: descending
9
+ sqlite_readable: |+
10
+ SELECT
11
+ "theaters"."id" AS 'id',
12
+ "theaters"."name" AS 'name'
13
+ FROM "theaters" "theaters"
14
+ ORDER BY "theaters"."created_at" DESC
15
+ sqlite_not_readable: |+
16
+ SELECT
17
+ "t0"."id" AS 'c0',
18
+ "t0"."name" AS 'c1'
19
+ FROM "theaters" "t0"
20
+ ORDER BY "t0"."created_at" DESC
21
+ mysql_readable: |+
22
+ SELECT
23
+ `theaters`.`id` AS 'id',
24
+ `theaters`.`name` AS 'name'
25
+ FROM `theaters` `theaters`
26
+ ORDER BY `theaters`.`created_at` DESC
27
+ mysql_not_readable: |+
28
+ SELECT
29
+ `t0`.`id` AS 'c0',
30
+ `t0`.`name` AS 'c1'
31
+ FROM `theaters` `t0`
32
+ ORDER BY `t0`.`created_at` DESC