ar_rollout 0.0.17 → 0.0.18
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.md +3 -0
- data/lib/ar_rollout/group.rb +20 -0
- data/lib/ar_rollout/membership.rb +10 -0
- data/lib/ar_rollout/opt_out.rb +5 -0
- data/lib/ar_rollout/rollout.rb +2 -0
- data/lib/ar_rollout/version.rb +1 -1
- data/lib/ar_rollout.rb +41 -11
- data/lib/generators/ar_rollout_generator.rb +2 -1
- data/lib/generators/templates/groups_migration.rb +19 -0
- data/lib/generators/templates/opt_outs_migration.rb +15 -0
- metadata +7 -2
data/README.md
CHANGED
@@ -118,6 +118,9 @@ List known features with:
|
|
118
118
|
- Merge ArRollout and Rollout class methods
|
119
119
|
- Autodetection of new features from code, before rollout begins
|
120
120
|
|
121
|
+
## Version 0.0.18 - 04 Dec 2012
|
122
|
+
- Add Group, Membership, OptOut
|
123
|
+
|
121
124
|
## Version 0.0.17 - 29 Nov 2012
|
122
125
|
- ArRollout caches groups
|
123
126
|
|
@@ -0,0 +1,20 @@
|
|
1
|
+
class Group < ActiveRecord::Base
|
2
|
+
after_destroy :destroy_rollouts
|
3
|
+
|
4
|
+
has_many :memberships, dependent: :destroy
|
5
|
+
validates :name, presence: true, uniqueness: true
|
6
|
+
validate :validate_not_defined
|
7
|
+
attr_accessible :name
|
8
|
+
|
9
|
+
private
|
10
|
+
|
11
|
+
def destroy_rollouts
|
12
|
+
Rollout.where(group: name).each(&:destroy)
|
13
|
+
end
|
14
|
+
|
15
|
+
def validate_not_defined
|
16
|
+
if ArRollout.defined_groups.include?(name.intern)
|
17
|
+
errors.add(:name, "can't be a defined group name")
|
18
|
+
end
|
19
|
+
end
|
20
|
+
end
|
data/lib/ar_rollout/rollout.rb
CHANGED
@@ -13,6 +13,8 @@ class Rollout < ActiveRecord::Base
|
|
13
13
|
def match_group?(user)
|
14
14
|
if Rollout.method_defined? "match_#{group}?"
|
15
15
|
send "match_#{group}?", user
|
16
|
+
elsif group = Group.find_by_name(group) && group.memberships.where('user_id = ?', user.id).any?
|
17
|
+
true
|
16
18
|
else
|
17
19
|
false
|
18
20
|
end
|
data/lib/ar_rollout/version.rb
CHANGED
data/lib/ar_rollout.rb
CHANGED
@@ -1,18 +1,25 @@
|
|
1
1
|
require 'ar_rollout/rollout.rb'
|
2
|
+
require 'ar_rollout/group.rb'
|
3
|
+
require 'ar_rollout/membership.rb'
|
4
|
+
require 'ar_rollout/opt_out.rb'
|
2
5
|
require 'ar_rollout/helper.rb'
|
3
6
|
module ArRollout
|
4
|
-
@@
|
7
|
+
@@defined_groups = []
|
5
8
|
|
6
9
|
def self.configure
|
7
10
|
yield self
|
8
11
|
end
|
9
12
|
|
13
|
+
def self.defined_groups
|
14
|
+
@@defined_groups
|
15
|
+
end
|
16
|
+
|
10
17
|
def self.groups
|
11
|
-
@@
|
18
|
+
(@@defined_groups + Group.select(:name).collect(&:name).collect(&:intern)).uniq.sort
|
12
19
|
end
|
13
20
|
|
14
21
|
def self.define_group(name, &block)
|
15
|
-
@@
|
22
|
+
@@defined_groups << name
|
16
23
|
|
17
24
|
Rollout.send :define_method, "match_#{name}?" do |b|
|
18
25
|
block.call(b)
|
@@ -30,8 +37,16 @@ module ArRollout
|
|
30
37
|
Rollout.find_all_by_name_and_user_id(feature, res_id).map(&:destroy)
|
31
38
|
end
|
32
39
|
|
40
|
+
def self.exclude_user(feature, user)
|
41
|
+
res_id = [Fixnum, String].include?(user.class) ? user : user.id
|
42
|
+
OptOut.create(feature: feature, user_id: res_id)
|
43
|
+
end
|
44
|
+
|
33
45
|
def self.activate_group(feature, group)
|
34
46
|
return false if feature.nil? || group.nil?
|
47
|
+
unless defined_groups.include? group
|
48
|
+
get_group(group)
|
49
|
+
end
|
35
50
|
Rollout.find_or_create_by_name_and_group(feature, group)
|
36
51
|
end
|
37
52
|
|
@@ -44,6 +59,15 @@ module ArRollout
|
|
44
59
|
Rollout.create(name: feature, percentage: percentage)
|
45
60
|
end
|
46
61
|
|
62
|
+
def self.get_group(group)
|
63
|
+
Group.find_or_create_by_name(group)
|
64
|
+
end
|
65
|
+
|
66
|
+
def self.activate_user_in_group(group, user)
|
67
|
+
res_id = [Fixnum, String].include?(user.class) ? user : user.id
|
68
|
+
Membership.find_or_create_by_group_id_and_user_id(get_group(group).id, res_id)
|
69
|
+
end
|
70
|
+
|
47
71
|
def self.deactivate_all(feature)
|
48
72
|
Rollout.find_all_by_name(feature).map(&:destroy)
|
49
73
|
end
|
@@ -52,10 +76,16 @@ module ArRollout
|
|
52
76
|
Rollout.select("distinct(name)").order(:name).map(&:name)
|
53
77
|
end
|
54
78
|
|
79
|
+
def self.active_groups
|
80
|
+
Rollout.where("'group' is NOT NULL").map(&:group).uniq
|
81
|
+
end
|
82
|
+
|
55
83
|
def self.active?(name, user)
|
56
84
|
return false unless user
|
57
|
-
|
58
|
-
|
85
|
+
unless OptOut.where(feature: name, user_id: user.id).any?
|
86
|
+
Rollout.where(name: name).where("user_id = ? or user_id is NULL", user.id.to_i).any? do |rollout|
|
87
|
+
rollout.match?(user)
|
88
|
+
end
|
59
89
|
end
|
60
90
|
end
|
61
91
|
|
@@ -79,22 +109,22 @@ module ArRollout
|
|
79
109
|
|
80
110
|
def self.info(feature)
|
81
111
|
{
|
82
|
-
:percentage => (
|
83
|
-
:groups =>
|
84
|
-
:users =>
|
112
|
+
:percentage => (_active_percentage(feature) || 0).to_i,
|
113
|
+
:groups => _active_groups(feature).map { |g| g.to_sym },
|
114
|
+
:users => _active_user_ids(feature)
|
85
115
|
}
|
86
116
|
end
|
87
117
|
|
88
118
|
private
|
89
|
-
def self.
|
119
|
+
def self._active_groups(feature)
|
90
120
|
Rollout.where('"name" = ? and "group" is not null', feature).map(&:group)
|
91
121
|
end
|
92
122
|
|
93
|
-
def self.
|
123
|
+
def self._active_user_ids(feature)
|
94
124
|
Rollout.where('"name" = ? and "user_id" is not null', feature).map(&:user_id)
|
95
125
|
end
|
96
126
|
|
97
|
-
def self.
|
127
|
+
def self._active_percentage(feature)
|
98
128
|
Rollout.select("percentage").where('"name" = ? and "percentage" is not null', feature).first
|
99
129
|
end
|
100
130
|
|
@@ -11,8 +11,9 @@ class ArRolloutGenerator < Rails::Generators::Base
|
|
11
11
|
def copy_initializer_file
|
12
12
|
copy_file "ar_rollout.rb", "config/initializers/ar_rollout.rb"
|
13
13
|
migration_template "migration.rb", "db/migrate/create_rollout"
|
14
|
+
migration_template "groups_migration.rb", "db/migrate/create_groups_and_groups_users"
|
15
|
+
migration_template "opt_outs_migration.rb", "db/migrate/create_opt_outs"
|
14
16
|
end
|
15
|
-
|
16
17
|
end
|
17
18
|
|
18
19
|
|
@@ -0,0 +1,19 @@
|
|
1
|
+
class CreateGroupsAndGroupsUsers < ActiveRecord::Migration
|
2
|
+
def up
|
3
|
+
create_table :groups do |t|
|
4
|
+
t.string :name
|
5
|
+
end
|
6
|
+
|
7
|
+
create_table :groups_users do |t|
|
8
|
+
t.references :group
|
9
|
+
t.references :user
|
10
|
+
end
|
11
|
+
|
12
|
+
add_index :groups_users, [:group_id, :user_id], unique: true
|
13
|
+
end
|
14
|
+
|
15
|
+
def down
|
16
|
+
drop_table :groups
|
17
|
+
drop_table :groups_users
|
18
|
+
end
|
19
|
+
end
|
@@ -0,0 +1,15 @@
|
|
1
|
+
class CreateOptOuts < ActiveRecord::Migration
|
2
|
+
def up
|
3
|
+
create_table :opt_outs do |t|
|
4
|
+
t.integer :user_id
|
5
|
+
t.string :feature
|
6
|
+
t.timestamps
|
7
|
+
end
|
8
|
+
|
9
|
+
add_index :opt_outs, [:user_id, :feature], unique: true
|
10
|
+
end
|
11
|
+
|
12
|
+
def down
|
13
|
+
drop_table :opt_outs
|
14
|
+
end
|
15
|
+
end
|
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: ar_rollout
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.0.
|
4
|
+
version: 0.0.18
|
5
5
|
prerelease:
|
6
6
|
platform: ruby
|
7
7
|
authors:
|
@@ -13,7 +13,7 @@ authors:
|
|
13
13
|
autorequire:
|
14
14
|
bindir: bin
|
15
15
|
cert_chain: []
|
16
|
-
date: 2012-
|
16
|
+
date: 2012-12-04 00:00:00.000000000 Z
|
17
17
|
dependencies:
|
18
18
|
- !ruby/object:Gem::Dependency
|
19
19
|
name: rails
|
@@ -86,13 +86,18 @@ executables: []
|
|
86
86
|
extensions: []
|
87
87
|
extra_rdoc_files: []
|
88
88
|
files:
|
89
|
+
- lib/ar_rollout/group.rb
|
89
90
|
- lib/ar_rollout/helper.rb
|
91
|
+
- lib/ar_rollout/membership.rb
|
92
|
+
- lib/ar_rollout/opt_out.rb
|
90
93
|
- lib/ar_rollout/rollout.rb
|
91
94
|
- lib/ar_rollout/version.rb
|
92
95
|
- lib/ar_rollout.rb
|
93
96
|
- lib/generators/ar_rollout_generator.rb
|
94
97
|
- lib/generators/templates/ar_rollout.rb
|
98
|
+
- lib/generators/templates/groups_migration.rb
|
95
99
|
- lib/generators/templates/migration.rb
|
100
|
+
- lib/generators/templates/opt_outs_migration.rb
|
96
101
|
- lib/tasks/ar_rollout_tasks.rake
|
97
102
|
- MIT-LICENSE
|
98
103
|
- Rakefile
|