similar_models 0.1.0 → 0.2.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/README.md +3 -3
- data/lib/similar_models/version.rb +1 -1
- data/lib/similar_models.rb +11 -12
- data/similar_models.gemspec +4 -4
- data/spec/spec_helper.rb +11 -1
- data/spec/support/schema.rb +1 -1
- metadata +10 -11
- data/.rspec +0 -2
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: ad504d7a2e4aff75dc1c3ff6d48162110aaedcad
|
4
|
+
data.tar.gz: 38cbf0ecea5b020f118845b893d59ab7bdb508c9
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: aebcd2acdddd464feedfc604300daf67add8022fa18920305f2849a31489f1dc8534ffe6eb21e02061be09ac89984194347f2997e496cd031a997b6988388864
|
7
|
+
data.tar.gz: aacfe230c5415df95ef1f4253cb837b53d559b5e770ceafaea9794611f3733fdb9219886c3ce6ae4053a70cc40f1531babd464483d22f69dd870340183f2e2ba
|
data/README.md
CHANGED
@@ -2,7 +2,7 @@
|
|
2
2
|
|
3
3
|
Adds a `similar_{model name plural}` method to an active record model, but can be set to any name using `as: {method name}`. It returns the most similar models of the same class based on associated models in common.
|
4
4
|
|
5
|
-
The association(s) have to be many to many, so either habtm or
|
5
|
+
The association(s) have to be many to many, so either [habtm](http://guides.rubyonrails.org/association_basics.html#the-has-and-belongs-to-many-association) or [has_many :through](http://guides.rubyonrails.org/association_basics.html#the-has-many-through-association).
|
6
6
|
|
7
7
|
## Installation
|
8
8
|
|
@@ -28,8 +28,8 @@ Post example
|
|
28
28
|
has_and_belongs_to_many :tags
|
29
29
|
|
30
30
|
has_similar_models :authors
|
31
|
-
has_similar_models :tags, as: :
|
32
|
-
has_similar_models :authors, :tags, as: :
|
31
|
+
has_similar_models :tags, as: :similar_posts_by_tag
|
32
|
+
has_similar_models :authors, :tags, as: :similar_posts_by_author_and_tag
|
33
33
|
end
|
34
34
|
|
35
35
|
class Tag < ActiveRecord::Base
|
data/lib/similar_models.rb
CHANGED
@@ -8,31 +8,30 @@ module SimilarModels
|
|
8
8
|
# defaults to 'def similar_{model name}'
|
9
9
|
define_method as do
|
10
10
|
table_name = self.class.table_name
|
11
|
+
primary_key = self.class.primary_key
|
12
|
+
primary_key_ref = "#{table_name}.#{primary_key}"
|
11
13
|
association_scopes = []
|
12
14
|
|
13
15
|
many_to_many_associations.each do |many_to_many_association|
|
14
16
|
assocation = self.class.reflect_on_association(many_to_many_association)
|
15
17
|
join_table, foreign_key, association_foreign_key = self.class.join_table_values(assocation)
|
16
18
|
|
17
|
-
association_scopes << self.class.where(
|
18
|
-
"
|
19
|
-
|
20
|
-
|
19
|
+
association_scopes << self.class.where(
|
20
|
+
"#{join_table}.#{association_foreign_key} IN \
|
21
|
+
(select #{join_table}.#{association_foreign_key} from #{join_table} \
|
22
|
+
where #{join_table}.#{foreign_key} = :foreign_key)", foreign_key: self.id
|
23
|
+
).joins("INNER JOIN #{join_table} ON #{join_table}.#{foreign_key} = #{primary_key_ref}")
|
21
24
|
end
|
22
25
|
|
23
|
-
scope = self.class.select("#{table_name}.*, count(#{
|
24
|
-
where.not(
|
25
|
-
group_by_clause =
|
26
|
+
scope = self.class.select("#{table_name}.*, count(#{primary_key_ref}) AS #{as}_model_count").
|
27
|
+
where.not(primary_key => self.id).order("#{as}_model_count DESC")
|
28
|
+
group_by_clause = primary_key
|
26
29
|
|
27
30
|
# if there is only one many-to-many association no need to use UNION sql syntax
|
28
31
|
if association_scopes.one?
|
29
32
|
scope.merge(association_scopes.first).group(group_by_clause)
|
30
33
|
else
|
31
|
-
|
32
|
-
# http://dba.stackexchange.com/questions/88988/postgres-error-column-must-appear-in-the-group-by-clause-or-be-used-in-an-aggre
|
33
|
-
if ActiveRecord::Base.connection.adapter_name == 'PostgreSQL'
|
34
|
-
group_by_clause = self.class.column_names.join(', ')
|
35
|
-
end
|
34
|
+
group_by_clause = self.class.column_names.join(', ')
|
36
35
|
|
37
36
|
# see http://blog.ubersense.com/2013/09/27/tech-talk-unioning-scoped-queries-in-rails/
|
38
37
|
scope.from("((#{association_scopes.map(&:to_sql).join(') UNION ALL (')})) AS #{table_name}").group(group_by_clause)
|
data/similar_models.gemspec
CHANGED
@@ -19,12 +19,12 @@ Gem::Specification.new do |spec|
|
|
19
19
|
spec.require_paths = ["lib"]
|
20
20
|
|
21
21
|
spec.required_ruby_version = '>= 2.1'
|
22
|
-
spec.add_runtime_dependency 'activerecord', '
|
23
|
-
spec.add_development_dependency 'bundler', '~> 1.
|
22
|
+
spec.add_runtime_dependency 'activerecord', '>= 4.2'
|
23
|
+
spec.add_development_dependency 'bundler', '~> 1.16'
|
24
24
|
spec.add_development_dependency 'rspec', '~> 3.5'
|
25
25
|
spec.add_development_dependency 'database_cleaner', '~>1.5'
|
26
26
|
spec.add_development_dependency 'sqlite3', '~>1.3'
|
27
|
-
spec.add_development_dependency 'mysql2', '~>0.
|
28
|
-
spec.add_development_dependency 'pg', '~>0
|
27
|
+
spec.add_development_dependency 'mysql2', '~>0.5'
|
28
|
+
spec.add_development_dependency 'pg', '~>1.0'
|
29
29
|
spec.add_development_dependency 'byebug', '~>9.0'
|
30
30
|
end
|
data/spec/spec_helper.rb
CHANGED
@@ -8,7 +8,7 @@
|
|
8
8
|
require 'active_record'
|
9
9
|
|
10
10
|
ActiveRecord::Base.establish_connection adapter: 'postgresql', database: 'similar_models'
|
11
|
-
# ActiveRecord::Base.establish_connection adapter: 'mysql2', database: 'similar_models'
|
11
|
+
# ActiveRecord::Base.establish_connection adapter: 'mysql2', database: 'similar_models', username: 'test'
|
12
12
|
# ActiveRecord::Base.establish_connection adapter: 'sqlite3', database: ':memory:'
|
13
13
|
load 'support/schema.rb'
|
14
14
|
|
@@ -24,6 +24,16 @@ RSpec.configure do |config|
|
|
24
24
|
config.run_all_when_everything_filtered = true
|
25
25
|
config.filter_run :focus
|
26
26
|
|
27
|
+
# Many RSpec users commonly either run the entire suite or an individual
|
28
|
+
# file, and it's useful to allow more verbose output when running an
|
29
|
+
# individual spec file.
|
30
|
+
if config.files_to_run.one?
|
31
|
+
# Use the documentation formatter for detailed output,
|
32
|
+
# unless a formatter has already been configured
|
33
|
+
# (e.g. via a command-line flag).
|
34
|
+
config.default_formatter = 'doc'
|
35
|
+
end
|
36
|
+
|
27
37
|
# Run specs in random order to surface order dependencies. If you find an
|
28
38
|
# order dependency and want to debug it, you can fix the order by providing
|
29
39
|
# the seed, which is printed after each run.
|
data/spec/support/schema.rb
CHANGED
metadata
CHANGED
@@ -1,27 +1,27 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: similar_models
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.
|
4
|
+
version: 0.2.0
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Jolyon Pawlyn
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date:
|
11
|
+
date: 2018-05-10 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: activerecord
|
15
15
|
requirement: !ruby/object:Gem::Requirement
|
16
16
|
requirements:
|
17
|
-
- - "
|
17
|
+
- - ">="
|
18
18
|
- !ruby/object:Gem::Version
|
19
19
|
version: '4.2'
|
20
20
|
type: :runtime
|
21
21
|
prerelease: false
|
22
22
|
version_requirements: !ruby/object:Gem::Requirement
|
23
23
|
requirements:
|
24
|
-
- - "
|
24
|
+
- - ">="
|
25
25
|
- !ruby/object:Gem::Version
|
26
26
|
version: '4.2'
|
27
27
|
- !ruby/object:Gem::Dependency
|
@@ -30,14 +30,14 @@ dependencies:
|
|
30
30
|
requirements:
|
31
31
|
- - "~>"
|
32
32
|
- !ruby/object:Gem::Version
|
33
|
-
version: '1.
|
33
|
+
version: '1.16'
|
34
34
|
type: :development
|
35
35
|
prerelease: false
|
36
36
|
version_requirements: !ruby/object:Gem::Requirement
|
37
37
|
requirements:
|
38
38
|
- - "~>"
|
39
39
|
- !ruby/object:Gem::Version
|
40
|
-
version: '1.
|
40
|
+
version: '1.16'
|
41
41
|
- !ruby/object:Gem::Dependency
|
42
42
|
name: rspec
|
43
43
|
requirement: !ruby/object:Gem::Requirement
|
@@ -86,28 +86,28 @@ dependencies:
|
|
86
86
|
requirements:
|
87
87
|
- - "~>"
|
88
88
|
- !ruby/object:Gem::Version
|
89
|
-
version: '0.
|
89
|
+
version: '0.5'
|
90
90
|
type: :development
|
91
91
|
prerelease: false
|
92
92
|
version_requirements: !ruby/object:Gem::Requirement
|
93
93
|
requirements:
|
94
94
|
- - "~>"
|
95
95
|
- !ruby/object:Gem::Version
|
96
|
-
version: '0.
|
96
|
+
version: '0.5'
|
97
97
|
- !ruby/object:Gem::Dependency
|
98
98
|
name: pg
|
99
99
|
requirement: !ruby/object:Gem::Requirement
|
100
100
|
requirements:
|
101
101
|
- - "~>"
|
102
102
|
- !ruby/object:Gem::Version
|
103
|
-
version: '0
|
103
|
+
version: '1.0'
|
104
104
|
type: :development
|
105
105
|
prerelease: false
|
106
106
|
version_requirements: !ruby/object:Gem::Requirement
|
107
107
|
requirements:
|
108
108
|
- - "~>"
|
109
109
|
- !ruby/object:Gem::Version
|
110
|
-
version: '0
|
110
|
+
version: '1.0'
|
111
111
|
- !ruby/object:Gem::Dependency
|
112
112
|
name: byebug
|
113
113
|
requirement: !ruby/object:Gem::Requirement
|
@@ -131,7 +131,6 @@ extensions: []
|
|
131
131
|
extra_rdoc_files: []
|
132
132
|
files:
|
133
133
|
- ".gitignore"
|
134
|
-
- ".rspec"
|
135
134
|
- ".ruby-version"
|
136
135
|
- Gemfile
|
137
136
|
- LICENSE.txt
|
data/.rspec
DELETED