1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
|
#!/usr/bin/ruby
#
# Copyright (c) 2004 Peter Palfrader <peter@palfrader.org>
#
# All rights reserved.
#
require "ldap"
require "yaml"
@config = YAML::load( File.open( '/etc/noreply/config' ) )
VALIDATION_REGEX = {
'uid' => /^[Wa-z.-]+$/,
'cn' => /^[Wa-z-]+$/,
'uidNumber' => /^[1-9][0-9]+$/,
'gidNumber' => /^[1-9][0-9]+$/,
'gecos' => /^[a-zA-Z0-9,. -]+$/,
'homeDirectory' => /^\/[a-zA-Z0-9.\/-]+$/,
'loginShell' => /^\/[a-zA-Z0-9\/-]+$/
}
5.times{
begin
@conn = LDAP::Conn.new(@config['ldapserver'], @config['ldapport'] )
break if @conn
rescue LDAP::ResultError
sleep 3
end
};
unless @conn.bind(@config['credentials']['ldap2passwd']['binddn'],
@config['credentials']['ldap2passwd']['bindpw'])
throw @conn.perror("bind")
end
def passwd_line(entry)
l = {}
%w(uid uidNumber gidNumber gecos homeDirectory loginShell).each{ |key|
next if ['gecos', 'loginShell'].include?(key) and not entry[key]
throw "key #{key} missing in #{entry['dn']}" unless entry[key]
throw "no validation regex for #{key}" unless VALIDATION_REGEX[key]
l[key] = entry[key].to_s
throw "value for #{key} (#{l[key]}) in #{entry['dn']} fails validation regex #{VALIDATION_REGEX[key]}" unless l[key] =~ VALIDATION_REGEX[key]
};
l['gecos'] = '' unless l['gecos']
l['loginShell'] = '/bin/false' unless l['loginShell']
sprintf "%s:x:%s:%s:%s:%s:%s\n", l['uid'], l['uidNumber'], l['gidNumber'], l['gecos'], l['homeDirectory'], l['loginShell']
end
def group_line(entry)
l = {}
%w(cn gidNumber).each{ |key|
throw "key #{key} missing in #{entry['dn']}" unless entry[key]
throw "no validation regex for #{key}" unless VALIDATION_REGEX[key]
l[key] = entry[key].to_s
throw "value for #{key} (#{l[key]}) in #{entry['dn']} fails validation regex #{VALIDATION_REGEX[key]}" unless l[key] =~ VALIDATION_REGEX[key]
};
members = []
if entry['memberUid']
entry['memberUid'].each{ |member|
throw "empty member value in group #{entry['dn']}" unless member
m = member.to_s
throw "member of group #{entry['dn']} fails UID validiation test" unless m =~ VALIDATION_REGEX['uid']
members << m
}
end
sprintf "%s:x:%s:%s\n", l['cn'], l['gidNumber'], members.join(',')
end
passwd_lines = []
passwd = @conn.search2(@config['basedn'], LDAP::LDAP_SCOPE_SUBTREE, '(objectClass=posixAccount)')
passwd.each{ |line|
passwd_lines << passwd_line(line)
}
group_lines = []
group = @conn.search2(@config['basedn'], LDAP::LDAP_SCOPE_SUBTREE, '(objectClass=posixGroup)')
group.each{ |line|
group_lines << group_line(line)
}
unless File.exists?('passwd') && (File.read('passwd') == passwd_lines.join())
f = File.new('passwd', 'w')
f.print passwd_lines.join
end
unless File.exists?('group') && (File.read('group') == group_lines.join())
f = File.new('group', 'w')
f.print group_lines.join
end
|