slug 0.5.7 → 0.6.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- data/README.rdoc +5 -3
- data/Rakefile +3 -3
- data/VERSION.yml +2 -2
- data/lib/slug.rb +4 -0
- data/lib/slug/slug.rb +7 -8
- data/slug.gemspec +10 -11
- data/test/models.rb +1 -1
- data/test/test_slug.rb +8 -4
- metadata +41 -17
data/README.rdoc
CHANGED
@@ -4,7 +4,7 @@ Slug provides simple, straightforward slugging for your ActiveRecord models.
|
|
4
4
|
|
5
5
|
Slug is based on code from Norman Clarke's fantastic {friendly_id}[http://friendly-id.rubyforge.org] project and Nick Zadrozny's {friendly_identifier}[http://code.google.com/p/friendly-identifier/].
|
6
6
|
|
7
|
-
|
7
|
+
What's different:
|
8
8
|
|
9
9
|
* Unlike friendly_id, slugs are stored directly in your model's table. friendly_id stores its data in a separate sluggable table, which enables cool things like slug versioning--but forces yet another join when trying to do complex find_by_slugs.
|
10
10
|
* Like friendly_id, diacritics (accented characters) are stripped from slug strings.
|
@@ -12,14 +12,16 @@ Here's what's different:
|
|
12
12
|
|
13
13
|
== INSTALLATION
|
14
14
|
|
15
|
-
sudo gem install slug
|
15
|
+
sudo gem install slug
|
16
16
|
|
17
17
|
then add
|
18
18
|
|
19
|
-
config.gem 'slug'
|
19
|
+
config.gem 'slug'
|
20
20
|
|
21
21
|
to your rails project.
|
22
22
|
|
23
|
+
Note that this version of slug is only compatible with Rails/active_support/active_record 3.x+. Rails 2 applications should use slug 0.5.3.
|
24
|
+
|
23
25
|
== USAGE
|
24
26
|
|
25
27
|
It's up to you to set up the appropriate column in your model. By default, Slug saves the slug to a column called 'slug', so in most cases you'll just want to add
|
data/Rakefile
CHANGED
@@ -8,13 +8,13 @@ begin
|
|
8
8
|
s.email = "ben.koski@gmail.com"
|
9
9
|
s.homepage = "http://github.com/bkoski/slug"
|
10
10
|
s.description = "Simple, straightforward slugs for your ActiveRecord models."
|
11
|
-
s.add_dependency 'activerecord'
|
12
|
-
s.add_dependency 'activesupport'
|
11
|
+
s.add_dependency 'activerecord', '> 3.0.0'
|
12
|
+
s.add_dependency 'activesupport', '> 3.0.0'
|
13
13
|
s.authors = ["Ben Koski"]
|
14
14
|
end
|
15
15
|
Jeweler::GemcutterTasks.new
|
16
16
|
rescue LoadError
|
17
|
-
puts "Jeweler not available. Install it with: sudo gem install
|
17
|
+
puts "Jeweler not available. Install it with: sudo gem install jeweler"
|
18
18
|
end
|
19
19
|
|
20
20
|
require 'rake/rdoctask'
|
data/VERSION.yml
CHANGED
data/lib/slug.rb
CHANGED
@@ -3,4 +3,8 @@ require File.join(File.dirname(__FILE__), 'slug', 'ascii_approximations')
|
|
3
3
|
|
4
4
|
if defined?(ActiveRecord)
|
5
5
|
ActiveRecord::Base.instance_eval { extend Slug::ClassMethods }
|
6
|
+
end
|
7
|
+
|
8
|
+
if defined?(Rails) && Rails.version.to_i < 3
|
9
|
+
raise "This version of slug requires Rails 3 or higher"
|
6
10
|
end
|
data/lib/slug/slug.rb
CHANGED
@@ -8,7 +8,7 @@ module Slug
|
|
8
8
|
#
|
9
9
|
# Options:
|
10
10
|
# * <tt>:column</tt> - the column the slug will be saved to (defaults to <tt>:slug</tt>)
|
11
|
-
# * <tt>:
|
11
|
+
# * <tt>:validate_uniquness_if</tt> - proc to determine whether uniqueness validation runs, same format as validates_uniquness_of :if
|
12
12
|
#
|
13
13
|
# Slug will take care of validating presence and uniqueness of slug.
|
14
14
|
|
@@ -24,12 +24,12 @@ module Slug
|
|
24
24
|
self.slug_column = opts.has_key?(:column) ? opts[:column] : :slug
|
25
25
|
|
26
26
|
uniqueness_opts = {}
|
27
|
-
uniqueness_opts
|
27
|
+
uniqueness_opts[:if] = opts[:validate_uniqueness_if] if opts.key?(:validate_uniqueness_if)
|
28
28
|
|
29
|
-
|
30
|
-
|
31
|
-
|
32
|
-
|
29
|
+
validates self.slug_column, :presence => { :message => "cannot be blank. Is #{self.slug_source} sluggable?" }
|
30
|
+
validates self.slug_column, :uniqueness => uniqueness_opts
|
31
|
+
validates self.slug_column, :format => { :with => /^[a-z0-9-]+$/, :message => "contains invalid characters. Only downcase letters, numbers, and '-' are allowed." }
|
32
|
+
before_validation :set_slug, :on => :create
|
33
33
|
end
|
34
34
|
end
|
35
35
|
|
@@ -113,8 +113,7 @@ module Slug
|
|
113
113
|
|
114
114
|
# Returns the next unique index for a slug.
|
115
115
|
def next_slug_sequence
|
116
|
-
last_in_sequence = self.class.
|
117
|
-
:order => "CAST(REPLACE(#{self.slug_column},'#{self[self.slug_column]}','') AS UNSIGNED)")
|
116
|
+
last_in_sequence = self.class.where("#{self.slug_column} LIKE ?", self[self.slug_column] + '%').order("CAST(REPLACE(#{self.slug_column},'#{self[self.slug_column]}-','') AS UNSIGNED) DESC").first
|
118
117
|
if last_in_sequence.nil?
|
119
118
|
return 0
|
120
119
|
else
|
data/slug.gemspec
CHANGED
@@ -5,11 +5,11 @@
|
|
5
5
|
|
6
6
|
Gem::Specification.new do |s|
|
7
7
|
s.name = %q{slug}
|
8
|
-
s.version = "0.
|
8
|
+
s.version = "0.6.0"
|
9
9
|
|
10
10
|
s.required_rubygems_version = Gem::Requirement.new(">= 0") if s.respond_to? :required_rubygems_version=
|
11
11
|
s.authors = ["Ben Koski"]
|
12
|
-
s.date = %q{
|
12
|
+
s.date = %q{2011-03-18}
|
13
13
|
s.description = %q{Simple, straightforward slugs for your ActiveRecord models.}
|
14
14
|
s.email = %q{ben.koski@gmail.com}
|
15
15
|
s.extra_rdoc_files = [
|
@@ -34,7 +34,7 @@ Gem::Specification.new do |s|
|
|
34
34
|
s.homepage = %q{http://github.com/bkoski/slug}
|
35
35
|
s.rdoc_options = ["--charset=UTF-8"]
|
36
36
|
s.require_paths = ["lib"]
|
37
|
-
s.rubygems_version = %q{1.
|
37
|
+
s.rubygems_version = %q{1.4.1}
|
38
38
|
s.summary = %q{Simple, straightforward slugs for your ActiveRecord models.}
|
39
39
|
s.test_files = [
|
40
40
|
"test/models.rb",
|
@@ -44,18 +44,17 @@ Gem::Specification.new do |s|
|
|
44
44
|
]
|
45
45
|
|
46
46
|
if s.respond_to? :specification_version then
|
47
|
-
current_version = Gem::Specification::CURRENT_SPECIFICATION_VERSION
|
48
47
|
s.specification_version = 3
|
49
48
|
|
50
|
-
if Gem::Version.new(Gem::
|
51
|
-
s.add_runtime_dependency(%q<activerecord>, ["
|
52
|
-
s.add_runtime_dependency(%q<activesupport>, ["
|
49
|
+
if Gem::Version.new(Gem::VERSION) >= Gem::Version.new('1.2.0') then
|
50
|
+
s.add_runtime_dependency(%q<activerecord>, ["> 3.0.0"])
|
51
|
+
s.add_runtime_dependency(%q<activesupport>, ["> 3.0.0"])
|
53
52
|
else
|
54
|
-
s.add_dependency(%q<activerecord>, ["
|
55
|
-
s.add_dependency(%q<activesupport>, ["
|
53
|
+
s.add_dependency(%q<activerecord>, ["> 3.0.0"])
|
54
|
+
s.add_dependency(%q<activesupport>, ["> 3.0.0"])
|
56
55
|
end
|
57
56
|
else
|
58
|
-
s.add_dependency(%q<activerecord>, ["
|
59
|
-
s.add_dependency(%q<activesupport>, ["
|
57
|
+
s.add_dependency(%q<activerecord>, ["> 3.0.0"])
|
58
|
+
s.add_dependency(%q<activesupport>, ["> 3.0.0"])
|
60
59
|
end
|
61
60
|
end
|
data/test/models.rb
CHANGED
@@ -14,7 +14,7 @@ class Company < ActiveRecord::Base
|
|
14
14
|
end
|
15
15
|
|
16
16
|
class Post < ActiveRecord::Base
|
17
|
-
slug :headline, :
|
17
|
+
slug :headline, :validate_uniqueness_if => Proc.new { false }
|
18
18
|
end
|
19
19
|
|
20
20
|
# Used to test slugs based on methods rather than database attributes
|
data/test/test_slug.rb
CHANGED
@@ -45,13 +45,13 @@ class TestSlug < Test::Unit::TestCase
|
|
45
45
|
article = Article.create
|
46
46
|
assert !article.valid?
|
47
47
|
require 'ruby-debug'
|
48
|
-
assert article.errors
|
48
|
+
assert article.errors[:slug]
|
49
49
|
end
|
50
50
|
|
51
51
|
should "set validation error if normalization makes source value empty" do
|
52
52
|
article = Article.create(:headline => '$$$')
|
53
53
|
assert !article.valid?
|
54
|
-
assert article.errors
|
54
|
+
assert article.errors[:slug]
|
55
55
|
end
|
56
56
|
|
57
57
|
should "not update the slug even if the source column changes" do
|
@@ -77,7 +77,7 @@ class TestSlug < Test::Unit::TestCase
|
|
77
77
|
assert article2.errors[:slug].present?
|
78
78
|
end
|
79
79
|
|
80
|
-
should "use
|
80
|
+
should "use validate_uniqueness_if proc to decide whether uniqueness validation applies" do
|
81
81
|
article1 = Post.create!(:headline => 'Test Headline')
|
82
82
|
article2 = Post.new
|
83
83
|
article2.slug = 'test-headline'
|
@@ -240,7 +240,11 @@ class TestSlug < Test::Unit::TestCase
|
|
240
240
|
12.times { |i| Article.create!(:headline => 'Test Headline') }
|
241
241
|
article_13 = Article.create!(:headline => 'Test Headline')
|
242
242
|
assert_equal 'test-headline-12', article_13.slug
|
243
|
-
|
243
|
+
|
244
|
+
12.times { |i| Article.create!(:headline => 'latest from lybia') }
|
245
|
+
article_13 = Article.create!(:headline => 'latest from lybia')
|
246
|
+
assert_equal 'latest-from-lybia-12', article_13.slug
|
247
|
+
end
|
244
248
|
end
|
245
249
|
|
246
250
|
end
|
metadata
CHANGED
@@ -1,7 +1,13 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: slug
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
|
4
|
+
hash: 7
|
5
|
+
prerelease:
|
6
|
+
segments:
|
7
|
+
- 0
|
8
|
+
- 6
|
9
|
+
- 0
|
10
|
+
version: 0.6.0
|
5
11
|
platform: ruby
|
6
12
|
authors:
|
7
13
|
- Ben Koski
|
@@ -9,29 +15,41 @@ autorequire:
|
|
9
15
|
bindir: bin
|
10
16
|
cert_chain: []
|
11
17
|
|
12
|
-
date:
|
18
|
+
date: 2011-03-18 00:00:00 -04:00
|
13
19
|
default_executable:
|
14
20
|
dependencies:
|
15
21
|
- !ruby/object:Gem::Dependency
|
16
22
|
name: activerecord
|
17
|
-
|
18
|
-
|
19
|
-
|
23
|
+
prerelease: false
|
24
|
+
requirement: &id001 !ruby/object:Gem::Requirement
|
25
|
+
none: false
|
20
26
|
requirements:
|
21
|
-
- - "
|
27
|
+
- - ">"
|
22
28
|
- !ruby/object:Gem::Version
|
23
|
-
|
24
|
-
|
29
|
+
hash: 7
|
30
|
+
segments:
|
31
|
+
- 3
|
32
|
+
- 0
|
33
|
+
- 0
|
34
|
+
version: 3.0.0
|
35
|
+
type: :runtime
|
36
|
+
version_requirements: *id001
|
25
37
|
- !ruby/object:Gem::Dependency
|
26
38
|
name: activesupport
|
27
|
-
|
28
|
-
|
29
|
-
|
39
|
+
prerelease: false
|
40
|
+
requirement: &id002 !ruby/object:Gem::Requirement
|
41
|
+
none: false
|
30
42
|
requirements:
|
31
|
-
- - "
|
43
|
+
- - ">"
|
32
44
|
- !ruby/object:Gem::Version
|
33
|
-
|
34
|
-
|
45
|
+
hash: 7
|
46
|
+
segments:
|
47
|
+
- 3
|
48
|
+
- 0
|
49
|
+
- 0
|
50
|
+
version: 3.0.0
|
51
|
+
type: :runtime
|
52
|
+
version_requirements: *id002
|
35
53
|
description: Simple, straightforward slugs for your ActiveRecord models.
|
36
54
|
email: ben.koski@gmail.com
|
37
55
|
executables: []
|
@@ -65,21 +83,27 @@ rdoc_options:
|
|
65
83
|
require_paths:
|
66
84
|
- lib
|
67
85
|
required_ruby_version: !ruby/object:Gem::Requirement
|
86
|
+
none: false
|
68
87
|
requirements:
|
69
88
|
- - ">="
|
70
89
|
- !ruby/object:Gem::Version
|
90
|
+
hash: 3
|
91
|
+
segments:
|
92
|
+
- 0
|
71
93
|
version: "0"
|
72
|
-
version:
|
73
94
|
required_rubygems_version: !ruby/object:Gem::Requirement
|
95
|
+
none: false
|
74
96
|
requirements:
|
75
97
|
- - ">="
|
76
98
|
- !ruby/object:Gem::Version
|
99
|
+
hash: 3
|
100
|
+
segments:
|
101
|
+
- 0
|
77
102
|
version: "0"
|
78
|
-
version:
|
79
103
|
requirements: []
|
80
104
|
|
81
105
|
rubyforge_project:
|
82
|
-
rubygems_version: 1.
|
106
|
+
rubygems_version: 1.4.1
|
83
107
|
signing_key:
|
84
108
|
specification_version: 3
|
85
109
|
summary: Simple, straightforward slugs for your ActiveRecord models.
|