settler 1.2.4 → 2.0.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +15 -0
- data/.travis.yml +14 -0
- data/Appraisals +15 -0
- data/CHANGELOG +7 -0
- data/Gemfile +10 -0
- data/Gemfile.lock +81 -0
- data/LICENSE +1 -1
- data/README.rdoc +14 -20
- data/Rakefile +2 -19
- data/VERSION +1 -1
- data/gemfiles/3.0.gemfile +10 -0
- data/gemfiles/3.0.gemfile.lock +73 -0
- data/gemfiles/3.2.gemfile +10 -0
- data/gemfiles/3.2.gemfile.lock +73 -0
- data/gemfiles/4.0.gemfile +10 -0
- data/gemfiles/4.0.gemfile.lock +81 -0
- data/lib/generators/settler/templates/migration.rb +1 -1
- data/lib/generators/settler/templates/settler.yml +4 -4
- data/lib/setting.rb +17 -32
- data/lib/settler.rb +4 -5
- data/settler.gemspec +22 -17
- data/test/schema.rb +1 -1
- data/test/settler.yml +8 -8
- data/test/{helper.rb → test_helper.rb} +2 -1
- data/test/test_settler.rb +9 -21
- metadata +28 -36
- data/generators/settler/settler_generator.rb +0 -13
- data/generators/settler/templates/migration.rb +0 -19
- data/generators/settler/templates/settler.yml +0 -30
- data/lib/default_scope_patch.rb +0 -17
- data/lib/hash_extension.rb +0 -9
- data/test/debug.log +0 -59876
@@ -0,0 +1,81 @@
|
|
1
|
+
GEM
|
2
|
+
remote: http://rubygems.org/
|
3
|
+
specs:
|
4
|
+
activemodel (4.0.0)
|
5
|
+
activesupport (= 4.0.0)
|
6
|
+
builder (~> 3.1.0)
|
7
|
+
activerecord (4.0.0)
|
8
|
+
activemodel (= 4.0.0)
|
9
|
+
activerecord-deprecated_finders (~> 1.0.2)
|
10
|
+
activesupport (= 4.0.0)
|
11
|
+
arel (~> 4.0.0)
|
12
|
+
activerecord-deprecated_finders (1.0.3)
|
13
|
+
activesupport (4.0.0)
|
14
|
+
i18n (~> 0.6, >= 0.6.4)
|
15
|
+
minitest (~> 4.2)
|
16
|
+
multi_json (~> 1.3)
|
17
|
+
thread_safe (~> 0.1)
|
18
|
+
tzinfo (~> 0.3.37)
|
19
|
+
addressable (2.3.5)
|
20
|
+
appraisal (0.5.2)
|
21
|
+
bundler
|
22
|
+
rake
|
23
|
+
arel (4.0.0)
|
24
|
+
atomic (1.1.12)
|
25
|
+
builder (3.1.4)
|
26
|
+
faraday (0.8.8)
|
27
|
+
multipart-post (~> 1.2.0)
|
28
|
+
git (1.2.5)
|
29
|
+
github_api (0.10.1)
|
30
|
+
addressable
|
31
|
+
faraday (~> 0.8.1)
|
32
|
+
hashie (>= 1.2)
|
33
|
+
multi_json (~> 1.4)
|
34
|
+
nokogiri (~> 1.5.2)
|
35
|
+
oauth2
|
36
|
+
hashie (2.0.5)
|
37
|
+
highline (1.6.19)
|
38
|
+
httpauth (0.2.0)
|
39
|
+
i18n (0.6.4)
|
40
|
+
jeweler (1.8.6)
|
41
|
+
builder
|
42
|
+
bundler (~> 1.0)
|
43
|
+
git (>= 1.2.5)
|
44
|
+
github_api (= 0.10.1)
|
45
|
+
highline (>= 1.6.15)
|
46
|
+
nokogiri (= 1.5.10)
|
47
|
+
rake
|
48
|
+
rdoc
|
49
|
+
json (1.8.0)
|
50
|
+
jwt (0.1.8)
|
51
|
+
multi_json (>= 1.5)
|
52
|
+
minitest (4.7.5)
|
53
|
+
multi_json (1.7.8)
|
54
|
+
multi_xml (0.5.5)
|
55
|
+
multipart-post (1.2.0)
|
56
|
+
nokogiri (1.5.10)
|
57
|
+
oauth2 (0.9.2)
|
58
|
+
faraday (~> 0.8)
|
59
|
+
httpauth (~> 0.2)
|
60
|
+
jwt (~> 0.1.4)
|
61
|
+
multi_json (~> 1.0)
|
62
|
+
multi_xml (~> 0.5)
|
63
|
+
rack (~> 1.2)
|
64
|
+
rack (1.5.2)
|
65
|
+
rake (10.1.0)
|
66
|
+
rdoc (4.0.1)
|
67
|
+
json (~> 1.4)
|
68
|
+
sqlite3 (1.3.7)
|
69
|
+
thread_safe (0.1.2)
|
70
|
+
atomic
|
71
|
+
tzinfo (0.3.37)
|
72
|
+
|
73
|
+
PLATFORMS
|
74
|
+
ruby
|
75
|
+
|
76
|
+
DEPENDENCIES
|
77
|
+
activerecord (~> 4.0)
|
78
|
+
activesupport (~> 4.0)
|
79
|
+
appraisal
|
80
|
+
jeweler
|
81
|
+
sqlite3
|
@@ -1,26 +1,26 @@
|
|
1
1
|
settings: &settings
|
2
2
|
google_analytics_key: &google
|
3
|
-
|
3
|
+
label: Google analytics key
|
4
4
|
value: 'UA-xxxxxx-x'
|
5
5
|
editable: true
|
6
6
|
deletable: false
|
7
7
|
validations:
|
8
8
|
presence: true
|
9
9
|
search_algorithm:
|
10
|
-
|
10
|
+
label: Default search engine
|
11
11
|
value: 'ferret'
|
12
12
|
editable: true
|
13
13
|
validations:
|
14
14
|
inclusion: [ 'ferret' , 'sphinx' ]
|
15
15
|
white_list:
|
16
|
-
|
16
|
+
label: 'White-listed words'
|
17
17
|
value: 'herp, derp'
|
18
18
|
|
19
19
|
development:
|
20
20
|
<<: *settings
|
21
21
|
google_analytics_key:
|
22
22
|
<<: *google
|
23
|
-
|
23
|
+
label: Development Google analytics key
|
24
24
|
value: 'UA-xxxxxx-1'
|
25
25
|
|
26
26
|
test:
|
data/lib/setting.rb
CHANGED
@@ -1,30 +1,20 @@
|
|
1
1
|
require 'type_casters'
|
2
|
-
require 'default_scope_patch' if defined?(ActiveRecord::VERSION) && ActiveRecord::VERSION::MAJOR >= 3
|
3
2
|
|
4
3
|
# The Setting class is an AR model that encapsulates a Settler setting. The key if the setting is the only required attribute.\
|
5
4
|
class Setting < ActiveRecord::Base
|
6
|
-
cattr_accessor :rails3
|
7
|
-
self.rails3 = defined?(ActiveRecord::VERSION) && ActiveRecord::VERSION::MAJOR >= 3
|
8
5
|
|
9
|
-
attr_readonly
|
10
|
-
|
11
|
-
|
12
|
-
validates_presence_of :key
|
13
|
-
validate :setting_validations
|
14
|
-
|
6
|
+
attr_readonly :key
|
7
|
+
|
15
8
|
serialize :value
|
16
9
|
|
17
|
-
|
18
|
-
|
19
|
-
|
20
|
-
|
21
|
-
|
22
|
-
default_scope :conditions => ['deleted = ? or deleted IS NULL', false]
|
23
|
-
end
|
10
|
+
validates :key, :presence => true
|
11
|
+
validate :setting_validations
|
12
|
+
validate :ensure_editable, :on => :update
|
13
|
+
|
14
|
+
default_scope { where(['deleted = ? or deleted IS NULL', false]) }
|
24
15
|
|
25
|
-
|
26
|
-
|
27
|
-
send scope_method, :deletable, :conditions => { :deletable => true }
|
16
|
+
scope :editable, lambda{ where(:editable => true) }
|
17
|
+
scope :deletable, lambda{ where(:deletable => true) }
|
28
18
|
|
29
19
|
# Returns the value, typecasted if a typecaster is available.
|
30
20
|
def value
|
@@ -55,7 +45,7 @@ class Setting < ActiveRecord::Base
|
|
55
45
|
end
|
56
46
|
|
57
47
|
def to_label
|
58
|
-
|
48
|
+
label.present? ? label : key
|
59
49
|
end
|
60
50
|
|
61
51
|
# Returns all valid values for this setting, which is based on the presence of an inclusion validator.
|
@@ -75,7 +65,7 @@ class Setting < ActiveRecord::Base
|
|
75
65
|
# Returns false if the setting could not be destroyed.
|
76
66
|
def destroy
|
77
67
|
if deletable?
|
78
|
-
self.deleted = true if Setting.
|
68
|
+
self.deleted = true if Setting.where(:id => self).update_all(:deleted => true)
|
79
69
|
deleted?
|
80
70
|
else
|
81
71
|
false
|
@@ -83,28 +73,23 @@ class Setting < ActiveRecord::Base
|
|
83
73
|
end
|
84
74
|
|
85
75
|
# Overrides the delete methods to ensure the default scope is not passed in the query
|
86
|
-
def delete *args; Setting.
|
87
|
-
def self.delete_all *args; Setting.
|
76
|
+
def delete *args; Setting.unscoped{ super } end
|
77
|
+
def self.delete_all *args; Setting.unscoped{ super } end
|
88
78
|
|
89
79
|
# Resets this setting to the default stored in the settler configuration
|
90
80
|
def reset!
|
91
81
|
defaults = Settler.config[self.key]
|
92
|
-
self.
|
82
|
+
self.label = defaults['label']
|
93
83
|
self.value = defaults['value']
|
94
84
|
self.editable = defaults['editable']
|
95
85
|
self.deletable = defaults['deletable']
|
96
86
|
self.deleted = false
|
97
|
-
|
98
|
-
end
|
99
|
-
|
100
|
-
# Can be used to get *all* settings, including deleted settings.
|
101
|
-
def self.without_default_scope &block
|
102
|
-
Setting.with_exclusive_scope(&block)
|
87
|
+
save(:validate => false)
|
103
88
|
end
|
104
89
|
|
105
90
|
# Deleted scope is specified as a method as it needs to be an exclusive scope
|
106
91
|
def self.deleted
|
107
|
-
|
92
|
+
unscoped { Setting.where(:deleted => true) }
|
108
93
|
end
|
109
94
|
|
110
95
|
private
|
@@ -130,7 +115,7 @@ private
|
|
130
115
|
|
131
116
|
# Ensures uneditable settings cannot be updated.
|
132
117
|
def ensure_editable
|
133
|
-
errors.add(:
|
118
|
+
errors.add(:base, I18n.t('settler.errors.editable', :default => 'Setting cannot be changed')) if changed? && !editable?
|
134
119
|
end
|
135
120
|
|
136
121
|
end
|
data/lib/settler.rb
CHANGED
@@ -1,6 +1,5 @@
|
|
1
1
|
require 'yaml'
|
2
2
|
require 'erb'
|
3
|
-
require 'hash_extension'
|
4
3
|
require 'type_casters'
|
5
4
|
require 'setting'
|
6
5
|
|
@@ -19,9 +18,9 @@ class Settler
|
|
19
18
|
self.config = File.exist?(source) ? YAML.load(ERB.new(File.read(source)).result).to_hash : {}
|
20
19
|
self.config = config[namespace] || {} if namespace
|
21
20
|
self.config.each do |key, attributes|
|
22
|
-
Setting.
|
23
|
-
setting = Setting.
|
24
|
-
s.
|
21
|
+
Setting.unscoped do
|
22
|
+
setting = Setting.where(:key => key).first || Setting.create(:key => key) do |s|
|
23
|
+
s.label = attributes['label']
|
25
24
|
s.value = attributes['value']
|
26
25
|
s.editable = attributes['editable']
|
27
26
|
s.deletable = attributes['deletable']
|
@@ -41,7 +40,7 @@ class Settler
|
|
41
40
|
# Returns an array of all setting keys
|
42
41
|
def settings(options = {})
|
43
42
|
Settler.load! if config.nil?
|
44
|
-
Setting.
|
43
|
+
Setting.order(options[:order]).pluck(:key)
|
45
44
|
end
|
46
45
|
|
47
46
|
# Returns a list of validations to perform on a setting.
|
data/settler.gemspec
CHANGED
@@ -5,11 +5,11 @@
|
|
5
5
|
|
6
6
|
Gem::Specification.new do |s|
|
7
7
|
s.name = "settler"
|
8
|
-
s.version = "
|
8
|
+
s.version = "2.0.0"
|
9
9
|
|
10
10
|
s.required_rubygems_version = Gem::Requirement.new(">= 0") if s.respond_to? :required_rubygems_version=
|
11
11
|
s.authors = ["Reinier de Lange"]
|
12
|
-
s.date = "
|
12
|
+
s.date = "2013-08-12"
|
13
13
|
s.description = "Settler can be used for defining application wide settings in Rails. Settings are loaded from a YAML file and stored in the database using ActiveRecord to allow users to update settings on the fly. The YAML configuration allows you to not only specify defaults, but setting value validations and typecasts as well!"
|
14
14
|
s.email = "r.j.delange@nedforce.nl"
|
15
15
|
s.extra_rdoc_files = [
|
@@ -18,50 +18,55 @@ Gem::Specification.new do |s|
|
|
18
18
|
]
|
19
19
|
s.files = [
|
20
20
|
".document",
|
21
|
+
".travis.yml",
|
22
|
+
"Appraisals",
|
23
|
+
"CHANGELOG",
|
24
|
+
"Gemfile",
|
25
|
+
"Gemfile.lock",
|
21
26
|
"LICENSE",
|
22
27
|
"README.rdoc",
|
23
28
|
"Rakefile",
|
24
29
|
"VERSION",
|
25
|
-
"
|
26
|
-
"
|
27
|
-
"
|
30
|
+
"gemfiles/3.0.gemfile",
|
31
|
+
"gemfiles/3.0.gemfile.lock",
|
32
|
+
"gemfiles/3.2.gemfile",
|
33
|
+
"gemfiles/3.2.gemfile.lock",
|
34
|
+
"gemfiles/4.0.gemfile",
|
35
|
+
"gemfiles/4.0.gemfile.lock",
|
28
36
|
"init.rb",
|
29
|
-
"lib/default_scope_patch.rb",
|
30
37
|
"lib/generators/settler/USAGE",
|
31
38
|
"lib/generators/settler/settler_generator.rb",
|
32
39
|
"lib/generators/settler/templates/migration.rb",
|
33
40
|
"lib/generators/settler/templates/settler.yml",
|
34
|
-
"lib/hash_extension.rb",
|
35
41
|
"lib/setting.rb",
|
36
42
|
"lib/settler.rb",
|
37
43
|
"lib/type_casters.rb",
|
38
44
|
"settler.gemspec",
|
39
45
|
"test/custom_typecaster.rb",
|
40
46
|
"test/database.yml",
|
41
|
-
"test/helper.rb",
|
42
47
|
"test/schema.rb",
|
43
48
|
"test/settler.yml",
|
49
|
+
"test/test_helper.rb",
|
44
50
|
"test/test_settler.rb"
|
45
51
|
]
|
46
52
|
s.homepage = "http://github.com/moiristo/settler"
|
47
53
|
s.require_paths = ["lib"]
|
48
|
-
s.rubygems_version = "
|
54
|
+
s.rubygems_version = "2.0.6"
|
49
55
|
s.summary = "Settler manages global application settings in Rails"
|
50
|
-
s.test_files = ["test/custom_typecaster.rb", "test/database.yml", "test/debug.log", "test/helper.rb", "test/schema.rb", "test/settler.yml", "test/test_settler.rb"]
|
51
56
|
|
52
57
|
if s.respond_to? :specification_version then
|
53
|
-
s.specification_version =
|
58
|
+
s.specification_version = 4
|
54
59
|
|
55
60
|
if Gem::Version.new(Gem::VERSION) >= Gem::Version.new('1.2.0') then
|
56
|
-
s.
|
57
|
-
s.add_runtime_dependency(%q<
|
61
|
+
s.add_runtime_dependency(%q<activerecord>, [">= 3.2"])
|
62
|
+
s.add_runtime_dependency(%q<activesupport>, [">= 3.2"])
|
58
63
|
else
|
59
|
-
s.add_dependency(%q<
|
60
|
-
s.add_dependency(%q<
|
64
|
+
s.add_dependency(%q<activerecord>, [">= 3.2"])
|
65
|
+
s.add_dependency(%q<activesupport>, [">= 3.2"])
|
61
66
|
end
|
62
67
|
else
|
63
|
-
s.add_dependency(%q<
|
64
|
-
s.add_dependency(%q<
|
68
|
+
s.add_dependency(%q<activerecord>, [">= 3.2"])
|
69
|
+
s.add_dependency(%q<activesupport>, [">= 3.2"])
|
65
70
|
end
|
66
71
|
end
|
67
72
|
|
data/test/schema.rb
CHANGED
data/test/settler.yml
CHANGED
@@ -1,6 +1,6 @@
|
|
1
1
|
settings:
|
2
2
|
google_analytics_key:
|
3
|
-
|
3
|
+
label: Google analytics key
|
4
4
|
value: 'UA-xxxxxx-x'
|
5
5
|
editable: true
|
6
6
|
deletable: false
|
@@ -8,34 +8,34 @@ settings:
|
|
8
8
|
format: !ruby/regexp "/^UA-.{6}-.$/i"
|
9
9
|
presence: true
|
10
10
|
search_algorithm:
|
11
|
-
|
11
|
+
label: Default search engine
|
12
12
|
value: 'ferret'
|
13
13
|
editable: false
|
14
14
|
deletable: true
|
15
15
|
validations:
|
16
16
|
inclusion: [ 'ferret' , 'sphinx' ]
|
17
17
|
bool_value:
|
18
|
-
|
18
|
+
label: A boolean that should be typecasted
|
19
19
|
value: true
|
20
20
|
typecast: boolean
|
21
21
|
float_value:
|
22
|
-
|
22
|
+
label: A float that should be typecasted
|
23
23
|
value: 0.25
|
24
24
|
typecast: float
|
25
25
|
integer_value:
|
26
|
-
|
26
|
+
label: An integer that should be typecasted
|
27
27
|
value: 3
|
28
28
|
typecast: integer
|
29
29
|
datetime_value:
|
30
|
-
|
30
|
+
label: A datetime that should be typecasted
|
31
31
|
value: "2012-01-15"
|
32
32
|
typecast: datetime
|
33
33
|
password_value:
|
34
|
-
|
34
|
+
label: A password value that should be typecasted
|
35
35
|
value: '123456'
|
36
36
|
typecast: password
|
37
37
|
custom_value:
|
38
|
-
|
38
|
+
label: An integer that should be custom typecasted
|
39
39
|
value: 1
|
40
40
|
typecast: CustomTypecaster
|
41
41
|
|
@@ -1,7 +1,7 @@
|
|
1
1
|
require 'rubygems'
|
2
|
-
#require 'debugger'
|
3
2
|
require 'test/unit'
|
4
3
|
require 'pp'
|
4
|
+
# require 'debugger'
|
5
5
|
|
6
6
|
$LOAD_PATH.unshift(File.join(File.dirname(__FILE__), '..', 'lib'))
|
7
7
|
$LOAD_PATH.unshift(File.dirname(__FILE__))
|
@@ -10,6 +10,7 @@ gem "activerecord"
|
|
10
10
|
require 'fileutils'
|
11
11
|
require 'active_record'
|
12
12
|
require 'active_support/core_ext/class/attribute_accessors'
|
13
|
+
require 'active_support/buffered_logger'
|
13
14
|
|
14
15
|
def load_schema
|
15
16
|
config = YAML::load(IO.read(File.dirname(__FILE__) + '/database.yml'))
|
data/test/test_settler.rb
CHANGED
@@ -1,8 +1,8 @@
|
|
1
|
-
require '
|
1
|
+
require 'test_helper'
|
2
2
|
|
3
3
|
class TestSettler < Test::Unit::TestCase
|
4
4
|
def setup
|
5
|
-
Setting.
|
5
|
+
Setting.delete_all
|
6
6
|
Settler.source = File.dirname(__FILE__) + '/settler.yml'
|
7
7
|
Settler.namespace = 'settings'
|
8
8
|
Settler.load!
|
@@ -36,13 +36,7 @@ class TestSettler < Test::Unit::TestCase
|
|
36
36
|
end
|
37
37
|
|
38
38
|
def test_should_not_create_instance
|
39
|
-
|
40
|
-
assert_nil Settler.new
|
41
|
-
else
|
42
|
-
assert_raise NoMethodError do
|
43
|
-
Settler.new
|
44
|
-
end
|
45
|
-
end
|
39
|
+
assert_nil Settler.new
|
46
40
|
end
|
47
41
|
|
48
42
|
def test_should_report_or_raise_missing
|
@@ -89,14 +83,14 @@ class TestSettler < Test::Unit::TestCase
|
|
89
83
|
def test_should_not_update_uneditable_setting
|
90
84
|
uneditable_setting = Settler.search_algorithm
|
91
85
|
assert !uneditable_setting.update_attributes(:value => 'sphinx')
|
92
|
-
assert
|
86
|
+
assert uneditable_setting.errors[:base].any?
|
93
87
|
assert_equal 'ferret', Settler[:search_algorithm]
|
94
88
|
end
|
95
89
|
|
96
90
|
def test_should_manually_update_uneditable_setting
|
97
91
|
uneditable_setting = Settler.search_algorithm
|
98
92
|
assert uneditable_setting.update_attribute(:value, 'sphinx')
|
99
|
-
assert
|
93
|
+
assert uneditable_setting.errors[:value].empty?
|
100
94
|
assert_equal 'sphinx', Settler[:search_algorithm]
|
101
95
|
end
|
102
96
|
|
@@ -112,16 +106,10 @@ class TestSettler < Test::Unit::TestCase
|
|
112
106
|
assert_equal 'google_analytics_key', setting.reload.key
|
113
107
|
end
|
114
108
|
|
115
|
-
def
|
116
|
-
setting = Settler.google_analytics_key
|
117
|
-
assert setting.update_attributes(:key => 'new_key', :
|
118
|
-
setting.
|
119
|
-
assert_equal 'google_analytics_key', setting.key
|
120
|
-
assert_equal 'new_alt', setting.alt
|
121
|
-
assert_equal 'UA-xxxxxx-1', setting.value
|
122
|
-
assert setting.editable?
|
123
|
-
assert !setting.deletable?
|
124
|
-
assert_nil setting.deleted
|
109
|
+
def test_should_not_update_uneditable_settings
|
110
|
+
setting = Settler.google_analytics_key
|
111
|
+
assert !setting.update_attributes(:key => 'new_key', :label => 'new_label', :value => 'UA-xxxxxx-1', :editable => false, :deletable => true, :deleted => true)
|
112
|
+
assert setting.errors[:base].any?
|
125
113
|
end
|
126
114
|
|
127
115
|
def test_should_get_scopes
|