Skip to content

Commit 0407a99

Browse files
committed
(MODULES-552) Add capability to specify column_privileges
1 parent fbef97d commit 0407a99

File tree

3 files changed

+47
-10
lines changed

3 files changed

+47
-10
lines changed

lib/puppet/provider/mysql_grant/mysql.rb

+14-5
Original file line numberDiff line numberDiff line change
@@ -29,11 +29,20 @@ def self.instances
2929
# Matching: GRANT (SELECT, UPDATE) PRIVILEGES ON (*.*) TO ('root')@('127.0.0.1') (WITH GRANT OPTION)
3030
if match = munged_grant.match(/^GRANT\s(.+)\sON\s(.+)\sTO\s(.*)@(.*?)(\s.*)$/)
3131
privileges, table, user, host, rest = match.captures
32-
# Once we split privileges up on the , we need to make sure we
33-
# shortern ALL PRIVILEGES to just all.
34-
stripped_privileges = privileges.split(',').map do |priv|
35-
priv == 'ALL PRIVILEGES' ? 'ALL' : priv.lstrip.rstrip
36-
end
32+
# split on ',' if it is not a non-'('-containing string followed by a
33+
# closing parenthesis ')'-char - e.g. only split comma separated elements not in
34+
# parentheses
35+
stripped_privileges = privileges.strip.split(/\s*,\s*(?![^(]*\))/).map{ |priv|
36+
# split and sort the column_privileges in the parentheses and rejoin
37+
if priv.include?('(')
38+
type, col=priv.strip.split(/\s+|\b/,2)
39+
type.upcase + " (" + col.slice(1...-1).strip.split(/\s*,\s*/).sort.join(', ') + ")"
40+
else
41+
# Once we split privileges up on the , we need to make sure we
42+
# shortern ALL PRIVILEGES to just all.
43+
priv == 'ALL PRIVILEGES' ? 'ALL' : priv.strip
44+
end
45+
}
3746
# Same here, but to remove OPTION leaving just GRANT.
3847
options = ['GRANT'] if rest.match(/WITH\sGRANT\sOPTION/)
3948
# fix double backslash that MySQL prints, so resources match

lib/puppet/type/mysql_grant.rb

+9-5
Original file line numberDiff line numberDiff line change
@@ -17,7 +17,15 @@ def initialize(*args)
1717
# Sort the privileges array in order to ensure the comparision in the provider
1818
# self.instances method match. Otherwise this causes it to keep resetting the
1919
# privileges.
20-
self[:privileges] = Array(self[:privileges]).map(&:upcase).uniq.reject{|k| k == 'GRANT' or k == 'GRANT OPTION'}.sort!
20+
self[:privileges] = Array(self[:privileges]).map{ |priv|
21+
# split and sort the column_privileges in the parentheses and rejoin
22+
if priv.include?('(')
23+
type, col=priv.strip.split(/\s+|\b/,2)
24+
type.upcase + " (" + col.slice(1...-1).strip.split(/\s*,\s*/).sort.join(', ') + ")"
25+
else
26+
priv.strip.upcase
27+
end
28+
}.uniq.reject{|k| k == 'GRANT' or k == 'GRANT OPTION'}.sort!
2129
end
2230

2331
validate do
@@ -37,10 +45,6 @@ def initialize(*args)
3745

3846
newproperty(:privileges, :array_matching => :all) do
3947
desc 'Privileges for user'
40-
41-
munge do |value|
42-
value.upcase
43-
end
4448
end
4549

4650
newproperty(:table) do

spec/unit/puppet/type/mysql_grant_spec.rb

+24
Original file line numberDiff line numberDiff line change
@@ -47,4 +47,28 @@
4747
}.to raise_error /name must match user and table parameters/
4848
end
4949

50+
describe 'it should munge privileges' do
51+
52+
it 'to just ALL' do
53+
@user = Puppet::Type.type(:mysql_grant).new(
54+
:name => 'foo@localhost/*.*', :table => ['*.*','@'], :user => 'foo@localhost',
55+
:privileges => ['ALL', 'PROXY'] )
56+
expect(@user[:privileges]).to eq(['ALL'])
57+
end
58+
59+
it 'to upcase and ordered' do
60+
@user = Puppet::Type.type(:mysql_grant).new(
61+
:name => 'foo@localhost/*.*', :table => ['*.*','@'], :user => 'foo@localhost',
62+
:privileges => ['select', 'Proxy'] )
63+
expect(@user[:privileges]).to eq(['PROXY', 'SELECT'])
64+
end
65+
66+
it 'ordered including column privileges' do
67+
@user = Puppet::Type.type(:mysql_grant).new(
68+
:name => 'foo@localhost/*.*', :table => ['*.*','@'], :user => 'foo@localhost',
69+
:privileges => ['SELECT(Host,Address)', 'Proxy'] )
70+
expect(@user[:privileges]).to eq(['PROXY', 'SELECT (Address, Host)'])
71+
end
72+
end
73+
5074
end

0 commit comments

Comments
 (0)