Class: Chef::TidyOrgAcls

Inherits:
Object
  • Object
show all
Defined in:
lib/chef/tidy_acls.rb

Instance Attribute Summary collapse

Instance Method Summary collapse

Constructor Details

#initialize(tidy, org) ⇒ TidyOrgAcls

Returns a new instance of TidyOrgAcls.



9
10
11
12
13
14
15
16
17
18
# File 'lib/chef/tidy_acls.rb', line 9

def initialize(tidy, org)
  @tidy = tidy
  @backup_path = @tidy.backup_path
  @org = org
  @clients = []
  @members = []
  @groups = []
  @users = []
  load_actors
end

Instance Attribute Details

#clientsObject

Returns the value of attribute clients.



7
8
9
# File 'lib/chef/tidy_acls.rb', line 7

def clients
  @clients
end

#groupsObject

Returns the value of attribute groups.



7
8
9
# File 'lib/chef/tidy_acls.rb', line 7

def groups
  @groups
end

#membersObject

Returns the value of attribute members.



7
8
9
# File 'lib/chef/tidy_acls.rb', line 7

def members
  @members
end

#usersObject

Returns the value of attribute users.



7
8
9
# File 'lib/chef/tidy_acls.rb', line 7

def users
  @users
end

Instance Method Details

#acl_actors_groups(acl) ⇒ Object



58
59
60
61
62
63
64
65
66
67
68
69
70
# File 'lib/chef/tidy_acls.rb', line 58

def acl_actors_groups(acl)
  actors_seen = []
  groups_seen = []
  acl_ops.each do |op|
    acl[op]["actors"].each do |actor|
      actors_seen.push(actor) unless actors_seen.include?(actor)
    end
    acl[op]["groups"].each do |group|
      groups_seen.push(group) unless groups_seen.include?(group)
    end
  end
  { actors: actors_seen, groups: groups_seen }
end

#acl_opsObject



54
55
56
# File 'lib/chef/tidy_acls.rb', line 54

def acl_ops
  %w{ create read update delete grant }
end

#add_actor_to_members(actor) ⇒ Object



117
118
119
120
121
122
# File 'lib/chef/tidy_acls.rb', line 117

def add_actor_to_members(actor)
  @tidy.ui.stdout.puts "REPAIRING: Invalid actor: #{actor} adding to #{@tidy.members_path(@org)}"
  user = { user: { username: actor } }
  @members.push(user)
  @tidy.write_new_file(@members, @tidy.members_path(@org))
end

#add_client_to_org(actor) ⇒ Object



112
113
114
115
# File 'lib/chef/tidy_acls.rb', line 112

def add_client_to_org(actor)
  # TODO
  @tidy.ui.stdout.puts "ACTION NEEDED: Client referenced in acl non-existent: #{actor}"
end

#ambiguous_actor?(actor) ⇒ Boolean

Returns:

  • (Boolean)


90
91
92
# File 'lib/chef/tidy_acls.rb', line 90

def ambiguous_actor?(actor)
  valid_org_member?(actor) && valid_org_client?(actor)
end

#default_client_acl(client_name) ⇒ Object



194
195
196
197
198
199
200
# File 'lib/chef/tidy_acls.rb', line 194

def default_client_acl(client_name)
  { create: { actors: ["pivotal", "#{@org}-validator", client_name], groups: ["admins"] },
    read: { actors: ["pivotal", "#{@org}-validator", client_name], groups: %w{admins users} },
    update: { actors: ["pivotal", client_name], groups: ["admins"] },
    delete: { actors: ["pivotal", client_name], groups: %w{admins users} },
    grant: { actors: ["pivotal", client_name], groups: ["admins"] } }
end

#default_user_acl(client) ⇒ Object



186
187
188
189
190
191
192
# File 'lib/chef/tidy_acls.rb', line 186

def default_user_acl(client)
  { create: { actors: ["pivotal", client], groups: ["::server-admins"] },
    read: { actors: ["pivotal", client], groups: ["::server-admins", "::#{@org}_read_access_group"] },
    update: { actors: ["pivotal", client], groups: ["::server-admins"] },
    delete: { actors: ["pivotal", client], groups: ["::server-admins"] },
    grant: { actors: ["pivotal", client], groups: ["::server-admins"] } }
end

#ensure_client_read_acls(acl_file) ⇒ Object



154
155
156
157
158
159
160
161
162
163
# File 'lib/chef/tidy_acls.rb', line 154

def ensure_client_read_acls(acl_file)
  acl = @tidy.json_file_to_hash(acl_file, symbolize_names: false)
  %w{users admins}.each do |group|
    unless acl["read"]["groups"].include? group
      @tidy.ui.stdout.puts "REPAIRING: Adding read acl for #{group} in #{acl_file}"
      acl["read"]["groups"].push(group)
    end
  end
  @tidy.write_new_file(acl, acl_file)
end

#ensure_global_group_acls(acl_file) ⇒ Object

Appends the proper acls for ::server-admins and the org’s read access group if they are missing.



139
140
141
142
143
144
145
146
147
148
149
150
151
152
# File 'lib/chef/tidy_acls.rb', line 139

def ensure_global_group_acls(acl_file)
  acl = @tidy.json_file_to_hash(acl_file, symbolize_names: false)
  acl_ops.each do |op|
    unless acl[op]["groups"].include? "::server-admins"
      @tidy.ui.stdout.puts "REPAIRING: Adding #{op} acl for ::server-admins in #{acl_file}"
      acl[op]["groups"].push("::server-admins")
    end
    if op == "read" && !acl[op]["groups"].include?("::#{@org}_read_access_group")
      @tidy.ui.stdout.puts "REPAIRING: Adding #{op} acl for ::#{@org}_read_access_group in #{acl_file}"
      acl[op]["groups"].push("::#{@org}_read_access_group")
    end
  end
  @tidy.write_new_file(acl, acl_file)
end

#fix_ambiguous_actor(actor) ⇒ Object



107
108
109
110
# File 'lib/chef/tidy_acls.rb', line 107

def fix_ambiguous_actor(actor)
  @tidy.ui.stdout.puts "REPAIRING: Ambiguous actor! #{actor} removing from #{@tidy.members_path(@org)}"
  remove_user_from_org(actor)
end

#invalid_group?(actor) ⇒ Boolean

Returns:

  • (Boolean)


84
85
86
87
88
# File 'lib/chef/tidy_acls.rb', line 84

def invalid_group?(actor)
  @groups.select { |group| group[:name] == actor }.empty? &&
    actor != "::server-admins" &&
    actor != "::#{@org}_read_access_group"
end

#load_actorsObject



46
47
48
49
50
51
52
# File 'lib/chef/tidy_acls.rb', line 46

def load_actors
  load_users
  load_members
  load_clients
  load_groups
  @tidy.ui.stdout.puts "INFO: #{@org} Actors loaded!"
end

#load_clientsObject



32
33
34
35
36
37
# File 'lib/chef/tidy_acls.rb', line 32

def load_clients
  @tidy.ui.stdout.puts "INFO: Loading clients for #{@org}"
  Dir[::File.join(@tidy.clients_path(@org), "*.json")].each do |client|
    @clients.push(@tidy.json_file_to_hash(client, symbolize_names: true))
  end
end

#load_groupsObject



39
40
41
42
43
44
# File 'lib/chef/tidy_acls.rb', line 39

def load_groups
  @tidy.ui.stdout.puts "INFO: Loading groups for #{@org}"
  Dir[::File.join(@tidy.groups_path(@org), "*.json")].each do |group|
    @groups.push(@tidy.json_file_to_hash(group, symbolize_names: true))
  end
end

#load_membersObject



27
28
29
30
# File 'lib/chef/tidy_acls.rb', line 27

def load_members
  @tidy.ui.stdout.puts "INFO: Loading members for #{@org}"
  @members = @tidy.json_file_to_hash(@tidy.members_path(@org), symbolize_names: true)
end

#load_usersObject



20
21
22
23
24
25
# File 'lib/chef/tidy_acls.rb', line 20

def load_users
  @tidy.ui.stdout.puts "INFO: Loading users"
  Dir[::File.join(@tidy.users_path, "*.json")].each do |user|
    @users.push(@tidy.json_file_to_hash(user, symbolize_names: true))
  end
end

#missing_from_members?(actor) ⇒ Boolean

Returns:

  • (Boolean)


94
95
96
# File 'lib/chef/tidy_acls.rb', line 94

def missing_from_members?(actor)
  valid_global_user?(actor) && !valid_org_member?(actor) && !valid_org_client?(actor)
end

#missing_org_client?(actor) ⇒ Boolean

Returns:

  • (Boolean)


98
99
100
# File 'lib/chef/tidy_acls.rb', line 98

def missing_org_client?(actor)
  !valid_global_user?(actor) && !valid_org_member?(actor) && !valid_org_client?(actor)
end

#org_aclsObject



102
103
104
105
# File 'lib/chef/tidy_acls.rb', line 102

def org_acls
  @org_acls ||= Dir[::File.join(@tidy.org_acls_path(@org), "**.json")] +
    Dir[::File.join(@tidy.org_acls_path(@org), "**", "*.json")]
end

#remove_group_from_acl(group, acl_file) ⇒ Object



129
130
131
132
133
134
135
136
# File 'lib/chef/tidy_acls.rb', line 129

def remove_group_from_acl(group, acl_file)
  @tidy.ui.stdout.puts "REPAIRING: Removing invalid group: #{group} from #{acl_file}"
  acl = @tidy.json_file_to_hash(acl_file, symbolize_names: false)
  acl_ops.each do |op|
    acl[op]["groups"].reject! { |the_group| the_group == group }
  end
  @tidy.write_new_file(acl, acl_file)
end

#remove_user_from_org(actor) ⇒ Object



124
125
126
127
# File 'lib/chef/tidy_acls.rb', line 124

def remove_user_from_org(actor)
  @members.reject! { |user| user[:user][:username] == actor }
  @tidy.write_new_file(@members, @tidy.members_path(@org))
end

#valid_global_user?(actor) ⇒ Boolean

Returns:

  • (Boolean)


80
81
82
# File 'lib/chef/tidy_acls.rb', line 80

def valid_global_user?(actor)
  !@users.select { |user| user[:username] == actor }.empty?
end

#valid_org_client?(actor) ⇒ Boolean

Returns:

  • (Boolean)


76
77
78
# File 'lib/chef/tidy_acls.rb', line 76

def valid_org_client?(actor)
  !@clients.select { |client| client[:name] == actor }.empty?
end

#valid_org_member?(actor) ⇒ Boolean

Returns:

  • (Boolean)


72
73
74
# File 'lib/chef/tidy_acls.rb', line 72

def valid_org_member?(actor)
  !@members.select { |user| user[:user][:username] == actor }.empty?
end

#validate_aclsObject



165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
# File 'lib/chef/tidy_acls.rb', line 165

def validate_acls
  org_acls.each do |acl_file|
    acl = @tidy.json_file_to_hash(acl_file, symbolize_names: false)
    actors_groups = acl_actors_groups(acl)
    actors_groups[:actors].each do |actor|
      next if actor == "pivotal"

      if ambiguous_actor?(actor)
        fix_ambiguous_actor(actor)
      elsif missing_from_members?(actor)
        add_actor_to_members(actor)
      elsif missing_org_client?(actor)
        add_client_to_org(actor)
      end
    end
    actors_groups[:groups].each do |group|
      remove_group_from_acl(group, acl_file) if invalid_group?(group)
    end
  end
end

#validate_client_aclsObject



220
221
222
223
224
225
226
227
228
229
230
231
232
# File 'lib/chef/tidy_acls.rb', line 220

def validate_client_acls
  @clients.each do |client|
    client_acl_path = ::File.join(@tidy.org_acls_path(@org), "clients", "#{client[:name]}.json")
    begin
      client_acl = @tidy.json_file_to_hash(client_acl_path, symbolize_names: false)
    rescue Errno::ENOENT
      @tidy.ui.stdout.puts "REPAIRING: Replacing missing client acl for #{client[:name]} in #{client_acl_path}."
      @tidy.write_new_file(default_client_acl(client[:name]), client_acl_path, backup = false)
      client_acl = @tidy.json_file_to_hash(client_acl_path, symbolize_names: false)
    end
    ensure_client_read_acls(client_acl_path)
  end
end

#validate_user_aclsObject



202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
# File 'lib/chef/tidy_acls.rb', line 202

def validate_user_acls
  @members.each do |member|
    user_acl_path = ::File.join(@tidy.user_acls_path, "#{member[:user][:username]}.json")
    begin
      user_acl = @tidy.json_file_to_hash(user_acl_path, symbolize_names: false)
    rescue Errno::ENOENT
      @tidy.ui.stdout.puts "REPAIRING: Replacing missing user acl for #{member[:user][:username]}."
      @tidy.write_new_file(default_user_acl(member), user_acl_path, backup = false)
      user_acl = @tidy.json_file_to_hash(user_acl_path, symbolize_names: false)
    end
    ensure_global_group_acls(user_acl_path)
    actors_groups = acl_actors_groups(user_acl)
    actors_groups[:groups].each do |group|
      remove_group_from_acl(group, user_acl_path) if invalid_group?(group)
    end
  end
end