sluggi 1.2.0 → 1.3.0

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 96fa3f419d83aa9dd9df2699072fc12c8c3e786b45fcf8d19fe7adca90fd5438
4
- data.tar.gz: 853a52b8ff87cb5833a56ca6d889f2cecce7d56763e6d5c9fed2b1a91a806368
3
+ metadata.gz: 8defbc5cc0371b0519aa658cafe635cca4fdde6dc72f0467d461dbece5626271
4
+ data.tar.gz: 8fd633be45bf0a35cc4853ea625c5368e219db60b60cca90f749fdf5ac7646e1
5
5
  SHA512:
6
- metadata.gz: 4f135200b99655e4437f10e077355f84bdcbe5b474eb72148644a0b9b72fc43a3d3da38f78b6f45951a98fc41bbdf36d60a6b711c93767763ac4cf91937ad423
7
- data.tar.gz: edd20ee1f9d8d63c3e3d6a21e1d51fb229b5bf35510d2b53b6029cdbbc2eedbfcc35cd4d70a25a701db9cdfbf0cd71256602af5d540af54eef5dcfd7944a0f99
6
+ metadata.gz: 6b49d66d863cdf218f9df93fe4d15e608148e2e77b7c280f62b56ea3e48d2abeb97a63b66a5058e65854f5c302c5dad04871586e4a98b415745cddc57402a208
7
+ data.tar.gz: 7d8dbae0fe73f1ecabcee3587364cfaa88cf65080fb20d4e4b172bf47c1f6d87bd6d5dd4d48c694577ef24077afc6f1bb7d014b5cf7d6cea36d6e2fbb6d9c24f
data/README.md CHANGED
@@ -3,7 +3,7 @@
3
3
  [![Gem Version](http://img.shields.io/gem/v/sluggi.svg)](http://rubygems.org/gems/sluggi)
4
4
  [![Build Status](http://img.shields.io/travis/neighborland/sluggi.svg)](https://travis-ci.org/neighborland/sluggi)
5
5
 
6
- Sluggi is a simple [friendly_id](https://github.com/norman/friendly_id)-inspired slugging library for ActiveRecord models.
6
+ Sluggi is a simple [friendly_id](https://github.com/norman/friendly_id)-inspired slugging library for ActiveRecord models. It is faster than `friendly_id` (see below for benchmarks).
7
7
 
8
8
  It provides basic slugs, slug history, and the ability to define multiple slug candidates.
9
9
 
@@ -129,20 +129,23 @@ Cat.find_by_slug('tuxedo-stan')
129
129
 
130
130
  ### Model with Slug Candidates
131
131
 
132
- Override `#slug_candidates` to define cascading candidate values for slugs. This is useful to avoid
133
- uniqueness conflicts.
132
+ Override `#slug_candidates` to define cascading candidate values for slugs.
133
+ This is useful to avoid uniqueness conflicts. Do not override `#slug_value` -
134
+ the default implementation in `Model` will call `#slug_candidates` and
135
+ works with or without `History`.
134
136
 
135
137
  ```ruby
136
138
  class Cat < ActiveRecord::Base
137
139
  include Sluggi::Slugged
138
140
 
139
- def name_and_id
140
- "#{name}-#{id}"
141
- end
142
-
143
- # the first unused value in the list is used
141
+ # The first unused value in the list is used.
142
+ # Each item may be a value or a lambda.
143
+ # Use a lambda to defer expensive unique value calculations.
144
144
  def slug_candidates
145
- [name, name_and_id]
145
+ [
146
+ name,
147
+ -> { "#{name}-#{Cat.count}" }
148
+ ]
146
149
  end
147
150
 
148
151
  def slug_value_changed?
@@ -158,11 +161,41 @@ cat.slug
158
161
 
159
162
  cat_2 = Cat.create(name: 'Tuxedo Stan')
160
163
  cat_2.slug
161
- => 'tuxedo-stan-2'
162
- cat_2.id
163
- => 2
164
+ => 'tuxedo-stan-456'
165
+ ```
166
+
167
+ ## Performance
168
+
169
+ Run the benchmark script: `ruby bench.rb`. This script is based on the
170
+ benchmark script from `friendly_id`.
171
+
172
+ Here are some anecdotal results using ruby 2.5.3:
164
173
 
165
174
  ```
175
+ SLUGGI FRIENDLY_ID
176
+ 1) find (id) - direct ActiveRecord 0.092318 0.093049
177
+ 2) find (in-table slug) 0.102773 0.259542
178
+ 3) find (in-table slug; using finders module) 0.098183 0.108248
179
+ 4) find (external slug) 0.670229 0.832791
180
+ 5) insert (plain AR / no slug) 0.345077 0.345105
181
+ 6) insert (in-table-slug) 0.666451 0.815505
182
+ 7) insert (in-table-slug; using finders module) 0.668737 0.744433
183
+ 8) insert (external slug) 2.480790 2.849761
184
+ ```
185
+
186
+ Notes:
187
+
188
+ Sluggi is at least 10% faster in every benchmark.
189
+
190
+ 1) Baseline (does not use either gem)
191
+ 2) 0.44x
192
+ 3) 0.90x
193
+ 4) 0.80x
194
+ 5) Baseline (does not use either gem)
195
+ 6) 0.82x
196
+ 7) 0.90x
197
+ 8) 0.87x
198
+
166
199
 
167
200
  ## Alternatives
168
201
 
@@ -39,11 +39,10 @@ module Sluggi
39
39
  end
40
40
 
41
41
  def create_slug
42
- value = clean_slug(slug_value)
43
- return if value.blank?
44
- return if slugs.first&.slug == value
45
- self.class.find_slugs(value).delete_all # revert to previous slug & put first
46
- slugs.create(slug: value)
42
+ return if slug.blank?
43
+ return if slugs.first&.slug == slug
44
+ self.class.find_slugs(slug).delete_all # revert to previous slug & put first
45
+ slugs.create(slug: slug)
47
46
  end
48
47
  end
49
48
  end
@@ -11,6 +11,13 @@ module Sluggi
11
11
  before_validation :set_slug
12
12
  end
13
13
 
14
+ module ClassMethods
15
+ # Define this so that History can override it.
16
+ def slug_exists?(name)
17
+ exists?(slug: name)
18
+ end
19
+ end
20
+
14
21
  def to_param
15
22
  errors.any? ? slug_was : slug
16
23
  end
@@ -31,11 +38,12 @@ module Sluggi
31
38
  # these are generally good to override:
32
39
 
33
40
  def slug_value
34
- slug_candidates.each do |value|
41
+ slug_candidates.each do |item|
42
+ value = item.respond_to?(:call) ? item.call : item
35
43
  next if value.blank?
36
44
  candidate = clean_slug(value)
37
45
  return candidate if candidate == slug
38
- return candidate unless self.class.exists?(slug: candidate)
46
+ return candidate unless self.class.slug_exists?(candidate)
39
47
  end
40
48
  nil
41
49
  end
@@ -1,5 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  module Sluggi
4
- VERSION = "1.2.0"
4
+ VERSION = "1.3.0"
5
5
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: sluggi
3
3
  version: !ruby/object:Gem::Version
4
- version: 1.2.0
4
+ version: 1.3.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Tee Parham
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2018-11-21 00:00:00.000000000 Z
11
+ date: 2018-11-24 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: activerecord