Revision 5174b503
Added by Marc Dequènes over 14 years ago
- ID 5174b503ce8e352baae3100d518158bf23758b87
.gitignore | ||
---|---|---|
lib/ldap_shadows/config_setup.rb
|
||
data/locale
|
||
#
|
||
conf/ldap_shadows/global_private.conf
|
||
conf/ldap_shadows/worlds/*/world_private.conf
|
||
var
|
bin/shadowwalker | ||
---|---|---|
:debug => false,
|
||
:expert => false,
|
||
:handles => false,
|
||
:world_name => nil,
|
||
:shadow_name => nil
|
||
}
|
||
|
||
... | ... | |
opt.on("-d", "--debug", "Output debug info without being formated") {|t| $program_options[:debug] = true }
|
||
opt.on("-e", "--expert", "Output extra info for expert users") {|t| $program_options[:expert] = true }
|
||
opt.on("-H", "--handles", "Output with handles (objects/field/... keys used for manipulations)") {|t| $program_options[:handles] = true }
|
||
opt.on("-w WORLD", "--world WORLD", "Choose world to enter") {|t| $program_options[:world_name] = t }
|
||
opt.on("-s SHADOW", "--shadow SHADOW", "Choose shadow to travel through") {|t| $program_options[:shadow_name] = t }
|
||
end
|
||
|
||
... | ... | |
|
||
def execute(args)
|
||
config = LdapShadows::Config.instance
|
||
config.load_global_config([File.join(ENV['HOME'], ".shadowwalker")])
|
||
config.load_world_config($program_options[:world_name], [File.join(ENV['HOME'], ".shadowwalker")])
|
||
begin
|
||
@shadow = config.load_shadow($program_options[:shadow_name])
|
||
rescue ActiveLdap::Error => e
|
conf/ldap_shadows/global.conf | ||
---|---|---|
---
|
||
default_shadow: MilkyPond
|
||
password_hash: ssha
|
||
default_world: MilkyPond
|
conf/ldap_shadows/shadows/MilkyPond/aspects/fs.conf | ||
---|---|---|
---
|
||
mapping:
|
||
classes: ['fsUser']
|
||
associated_relations: ['primaryGroup', 'secondaryGroups']
|
||
relations:
|
||
primaryGroup:
|
||
type: belongs_to
|
||
object: group
|
||
foreign_key: gidNumber
|
||
primary_key: gidNumber
|
||
secondaryGroups:
|
||
type: belongs_to
|
||
object: group
|
||
many: uniqueMember
|
||
primary_key: dn
|
||
plugin:
|
||
min_uid: 10000
|
||
max_uid: 65535
|
||
step_uid: 100
|
||
default_group: dc-users
|
||
default_home_base: '/home'
|
conf/ldap_shadows/shadows/MilkyPond/aspects/ftp.conf | ||
---|---|---|
---
|
||
mapping:
|
||
classes: ['ftpUser']
|
||
depend_aspects: ['primary_account', 'fs']
|
conf/ldap_shadows/shadows/MilkyPond/aspects/jabber.conf | ||
---|---|---|
---
|
||
mapping:
|
||
classes: ['jabberUser']
|
conf/ldap_shadows/shadows/MilkyPond/aspects/mail.conf | ||
---|---|---|
---
|
||
mapping:
|
||
classes: ['emailUser']
|
conf/ldap_shadows/shadows/MilkyPond/aspects/primary_account.conf | ||
---|---|---|
---
|
||
mapping:
|
||
classes: ['primaryAccount']
|
||
associated_attributes: ['uid', 'allowedServices']
|
conf/ldap_shadows/shadows/MilkyPond/aspects/shell.conf | ||
---|---|---|
---
|
||
mapping:
|
||
classes: ['shellUser']
|
||
depend_aspects: ['primary_account', 'fs']
|
||
associated_attributes: ['loginShell']
|
conf/ldap_shadows/shadows/MilkyPond/aspects/web.conf | ||
---|---|---|
---
|
||
mapping:
|
||
classes: ['webUser']
|
||
depend_aspects: ['primary_account']
|
conf/ldap_shadows/shadows/MilkyPond/objects/bot.conf | ||
---|---|---|
---
|
||
mapping:
|
||
dn_attribute: uid
|
||
prefix: ''
|
||
classes: ['bot']
|
||
sort_by: uid
|
||
possible_aspects: ['primary_account', 'mail', 'fs', 'shell', 'ftp', 'web', 'jabber']
|
||
default_parent: "unit/SpecialAccounts"
|
||
presentation:
|
||
hidden_attributes: ['uid']
|
||
expert_attributes: ['uidNumber', 'gidNumber', 'gecos']
|
conf/ldap_shadows/shadows/MilkyPond/objects/domain.conf | ||
---|---|---|
---
|
||
mapping:
|
||
dn_attribute: cn
|
||
prefix: ''
|
||
classes: ['genericDomain']
|
||
sort_by: cn
|
||
parent_handle_restrictions: "^(unit/Domains|(individual|bot)/.+)$"
|
||
default_parent: "unit/Domains"
|
||
|
conf/ldap_shadows/shadows/MilkyPond/objects/entity.conf | ||
---|---|---|
---
|
||
mapping:
|
||
dn_attribute: o
|
||
prefix: ''
|
||
classes: ['entity']
|
||
excluded_classes: ['dcObject']
|
||
sort_by: o
|
||
associated_relations: ['foundersIndividuals', 'foundersEntities']
|
||
parent_handle_restrictions: "^unit/Entities$"
|
||
default_parent: "unit/Entities"
|
||
presentation:
|
||
name_attribute: o
|
||
hidden_attributes: ['founder']
|
||
relations:
|
||
foundersIndividuals:
|
||
type: has_many
|
||
object: individual
|
||
foreign_key: founder
|
||
primary_key: dn
|
||
foundersEntities:
|
||
type: has_many
|
||
object: entity
|
||
foreign_key: founder
|
||
primary_key: dn
|
conf/ldap_shadows/shadows/MilkyPond/objects/group.conf | ||
---|---|---|
---
|
||
mapping:
|
||
dn_attribute: cn
|
||
prefix: ''
|
||
classes: ['posixGroup', 'groupOfMembers']
|
||
sort_by: cn
|
||
associated_relations: ['individualsPrimaryMembers', 'botsPrimaryMembers', 'individualsSecondaryMembers', 'botsSecondaryMembers']
|
||
presentation:
|
||
hidden_attributes: ['uniqueMember']
|
||
expert_attributes: ['gidNumber']
|
||
relations:
|
||
individualsPrimaryMembers:
|
||
type: belongs_to
|
||
object: individual
|
||
many: gidNumber
|
||
primary_key: gidNumber
|
||
botsPrimaryMembers:
|
||
type: belongs_to
|
||
object: bot
|
||
many: gidNumber
|
||
primary_key: gidNumber
|
||
individualsSecondaryMembers:
|
||
type: has_many
|
||
object: individual
|
||
foreign_key: uniqueMember
|
||
primary_key: dn
|
||
botsSecondaryMembers:
|
||
type: has_many
|
||
object: bot
|
||
foreign_key: uniqueMember
|
||
primary_key: dn
|
conf/ldap_shadows/shadows/MilkyPond/objects/individual.conf | ||
---|---|---|
---
|
||
mapping:
|
||
dn_attribute: uid
|
||
prefix: ''
|
||
classes: ['individual']
|
||
sort_by: uid
|
||
possible_aspects: ['primary_account', 'mail', 'fs', 'shell', 'ftp', 'web', 'jabber']
|
||
parent_handle_restrictions: "^unit/People$"
|
||
default_parent: "unit/People"
|
||
presentation:
|
||
hidden_attributes: ['uid']
|
||
expert_attributes: ['uidNumber', 'gidNumber', 'gecos']
|
conf/ldap_shadows/shadows/MilkyPond/objects/secondary_account.conf | ||
---|---|---|
---
|
||
mapping:
|
||
dn_attribute: uid
|
||
prefix: ''
|
||
classes: ['secondaryAccount']
|
||
sort_by: uid
|
||
possible_aspects: ['mail', 'fs', 'shell', 'ftp', 'web', 'jabber']
|
||
parent_handle_restrictions: "^(unit/SpecialAccounts|(individual|bot|domain)/.+)$"
|
||
default_parent: "unit/SpecialAccounts"
|
||
associated_attributes: ['uid', 'allowedServices']
|
conf/ldap_shadows/shadows/MilkyPond/objects/system_account.conf | ||
---|---|---|
---
|
||
mapping:
|
||
dn_attribute: uid
|
||
prefix: ''
|
||
classes: ['systemAccount']
|
||
sort_by: uid
|
||
possible_aspects: ['mail', 'fs', 'shell', 'ftp', 'web', 'jabber']
|
||
default_parent: "unit/SpecialAccounts"
|
||
associated_attributes: ['uid', 'allowedServices']
|
conf/ldap_shadows/shadows/MilkyPond/objects/top_entity.conf | ||
---|---|---|
---
|
||
mapping:
|
||
dn_attribute: dc
|
||
prefix: ''
|
||
classes: ['entity', 'dcObject']
|
||
sort_by: o
|
||
parent_handle_restrictions: "^$"
|
||
presentation:
|
||
name_attribute: o
|
conf/ldap_shadows/shadows/MilkyPond/objects/unit.conf | ||
---|---|---|
---
|
||
mapping:
|
||
dn_attribute: ou
|
||
prefix: ''
|
||
classes: ['organizationalUnit']
|
||
# no sort_by means sort by DN
|
||
presentation:
|
||
name_attribute: dn
|
conf/ldap_shadows/shadows/MilkyPond/objects/user_service.conf | ||
---|---|---|
---
|
||
mapping:
|
||
dn_attribute: cn
|
||
prefix: ''
|
||
classes: ['userService']
|
||
sort_by: cn
|
||
possible_aspects: []
|
||
parent_handle_restrictions: "^unit/ProvidedServices$"
|
conf/ldap_shadows/shadows/MilkyPond/plugins/aspects/fs.rb | ||
---|---|---|
|
||
def self.hook_before_create(item)
|
||
hook_common(item)
|
||
end
|
||
|
||
def self.hook_before_modify(item)
|
||
hook_common(item)
|
||
end
|
||
|
||
def self.hook_common(item)
|
||
pconfig_default = {
|
||
:default_group => 'users',
|
||
:min_uid => 1000,
|
||
:max_uid => 65535,
|
||
:step_uid => 100,
|
||
:default_home_base => "/home"
|
||
}
|
||
pconfig = pconfig_default.merge(self.parameters[:plugin])
|
||
|
||
unless item.attribute_present?('gidNumber')
|
||
item.primaryGroup = item.class.shadow.get_object(:group).find(:first, pconfig[:default_group])
|
||
end
|
||
|
||
if item.attribute_present?('uidNumber')
|
||
user = ActiveLdap::Base.find(:first, :scope => :sub, :filter => "(&(objectClass=posixAccount)(uidNumber=#{item.uidNumber}))", :attributes => ['uidNumber'])
|
||
unless user.nil? or user.dn == item.dn
|
||
raise_error "UID already used by another item"
|
||
end
|
||
else
|
||
users = ActiveLdap::Base.find(:all, :scope => :sub, :filter => "(&(objectClass=posixAccount)(uidNumber=*))", :attributes => ['uidNumber'])
|
||
uidnumbers = users.collect {|user| user.uidNumber }
|
||
|
||
avail_uidnumber = nil
|
||
min_uidn = pconfig[:min_uid]
|
||
max_uidn = [min_uidn + pconfig[:step_uid], pconfig[:max_uid]].min
|
||
while avail_uidnumber.nil?
|
||
avail = (min_uidn..max_uidn).to_a - uidnumbers
|
||
unless avail.empty?
|
||
avail_uidnumber = avail.first
|
||
break
|
||
end
|
||
min_uidn = max_uidn
|
||
max_uidn = [min_uidn + pconfig[:step_uid], pconfig[:max_uid]].min
|
||
end
|
||
|
||
if avail_uidnumber.nil?
|
||
raise_error "Available UID range is depleted."
|
||
else
|
||
item.uidNumber = avail_uidnumber
|
||
end
|
||
end
|
||
|
||
unless item.attribute_present?('homeDirectory')
|
||
item.homeDirectory = File.join(pconfig[:default_home_base], item.uid)
|
||
end
|
||
end
|
conf/ldap_shadows/shadows/MilkyPond/plugins/aspects/primary_account.rb | ||
---|---|---|
|
||
require 'shared_attributes'
|
||
|
||
def self.hook_before_create(item)
|
||
hook_common(item)
|
||
end
|
||
|
||
def self.hook_before_modify(item)
|
||
hook_common(item)
|
||
end
|
||
|
||
def self.hook_common(item)
|
||
SharedAttr.check_common_attributes(item)
|
||
end
|
||
|
conf/ldap_shadows/shadows/MilkyPond/plugins/includes/shared_attributes.rb | ||
---|---|---|
module SharedAttr
|
||
module_function
|
||
|
||
def check_common_attributes(item)
|
||
if item.attribute_present?('allowedServices')
|
||
user_services = ActiveLdap::Base.find(:all, :scope => :sub, :filter => "(objectClass=userService)", :attributes => ['cn'])
|
||
srv_names = user_services.collect {|srv| srv.cn }
|
||
|
||
invalid_srv_names = item.allowedServices(true) - (item.allowedServices(true) & srv_names)
|
||
unless invalid_srv_names.empty?
|
||
raise PreProcessingError, "Invalid User Service(s) name(s): " + invalid_srv_names.join(", ")
|
||
end
|
||
end
|
||
end
|
||
end
|
conf/ldap_shadows/shadows/MilkyPond/plugins/objects/individual.rb | ||
---|---|---|
|
||
def self.hook_before_create(item)
|
||
unless item.attribute_present?('cn')
|
||
cn = item.surname || ""
|
||
cn = item.givenName + " " + cn if item.givenName
|
||
item.cn = cn
|
||
end
|
||
end
|
||
|
conf/ldap_shadows/shadows/MilkyPond/plugins/objects/secondary_account.rb | ||
---|---|---|
|
||
require 'shared_attributes'
|
||
|
||
def self.hook_before_create(item)
|
||
hook_common(item)
|
||
end
|
||
|
||
def self.hook_before_modify(item)
|
||
hook_common(item)
|
||
end
|
||
|
||
def self.hook_common(item)
|
||
SharedAttr.check_common_attributes(item)
|
||
end
|
||
|
conf/ldap_shadows/shadows/MilkyPond/plugins/objects/system_account.rb | ||
---|---|---|
|
||
require 'shared_attributes'
|
||
|
||
def self.hook_before_create(item)
|
||
hook_common(item)
|
||
end
|
||
|
||
def self.hook_before_modify(item)
|
||
hook_common(item)
|
||
end
|
||
|
||
def self.hook_common(item)
|
||
SharedAttr.check_common_attributes(item)
|
||
end
|
||
|
conf/ldap_shadows/shadows/MilkyPond/shadow.conf | ||
---|---|---|
---
|
||
presentation:
|
||
hidden_attributes: ['objectClass', 'userPassword', 'hasSubordinates', 'entryUUID', 'entryDN', 'structuralObjectClass', 'subschemaSubentry']
|
||
tree_objects: ['unit', 'entity']
|
conf/ldap_shadows/shadows/MilkyPond/translations/en.yml | ||
---|---|---|
---
|
||
en:
|
||
objects:
|
||
bot: "Bot"
|
||
domain: "Domain"
|
||
entity: "Entity"
|
||
group: "Group"
|
||
individual: "Individual"
|
||
secondary_account: "Secondary Account"
|
||
system_account: "System Account"
|
||
unit: "Unit"
|
||
user_service: "User Service"
|
||
attribute_types:
|
||
allowGlobalDirectory: "Disclose Own Contact Information in GLobal Directory"
|
||
cn: "Full Name"
|
||
createTimestamp: "Item creation time"
|
||
creatorsName: "Item Creator"
|
||
birthday: "Birthday"
|
||
birthlocation: "Birth Location"
|
||
description: "Description"
|
||
entryUUID: "Item UUID"
|
||
foundingDate: "Founding Date"
|
||
ftpHost: "FTP Allowed Hosts"
|
||
gecos: "GECOS"
|
||
gidNumber: "Primary Group (numeric)"
|
||
givenName: "FirstName"
|
||
homeDirectory: "Home Directory"
|
||
homePostalAddress: "Home Postal Address"
|
||
host: "Shell Allowed Hosts"
|
||
ipServiceName: "Service Name"
|
||
ipServiceHost: "Service Host"
|
||
ipServicePort: "Service Port"
|
||
ipServiceProtocol: "Service Protocol"
|
||
jid: "Jabber ID"
|
||
jpegPhoto: "Photo"
|
||
keyFingerPrint: "GPG/PGP Key Fingerprint"
|
||
labeledURI: "Web Site"
|
||
loginShell: "Shell Interpreter"
|
||
mail: "eMail address(es)"
|
||
mailForward: "eMail Forward Adress(es)"
|
||
mailQuota: "Maximum Mailbox Size"
|
||
manager: "Manager(s)"
|
||
mobile: "Mobile Phone"
|
||
modifiersName: "Item Last Modifier"
|
||
modifyTimestamp: "Item Last Modification Time"
|
||
occupation: "Job / Studies"
|
||
o: "Organization(s)"
|
||
structuralObjectClass: "Item Structural Classes"
|
||
owner: "Owner(s)"
|
||
preferredLanguage: "Language Preference"
|
||
sn: "Surname"
|
||
sshAuthKey: "SSH Public Key(s)"
|
||
uid: "Identifier (Login)"
|
||
uidNumber: "Identifier (numeric)"
|
||
uniqueAbbreviation: "Unique Abbreviation"
|
||
uniqueMember: "Group member"
|
||
userPassword: "Password"
|
||
webVirtualHost: "Hosted Web Sites"
|
||
allowedServices: "Authorized services"
|
||
relations:
|
||
primaryGroup: "Primary Group"
|
||
secondaryGroups: "Secondary Groups"
|
||
individualsPrimaryMembers: "Primary Member(s) Individual(s)"
|
||
botsPrimaryMembers: "Primary Member(s) Bot(s)"
|
||
individualsSecondaryMembers: "Secondary Member(s) Individual(s)"
|
||
botsSecondaryMembers: "Secondary Member(s) Bot(s)"
|
||
foundersIndividuals: "Founder(s) Individual(s)"
|
||
foundersEntities: "Founder(s) Entity(ies)"
|
||
aspects:
|
||
fs: "FileSystem Account"
|
||
ftp: "FTP Account"
|
||
jabber: "Jabber Account"
|
||
mail: "eMail Account"
|
||
primary_account: "Primary Account"
|
||
shell: "Shell Account"
|
||
web: "Web Account"
|
conf/ldap_shadows/worlds/MilkyPond/shadows/Administration/aspects/fs.conf | ||
---|---|---|
---
|
||
mapping:
|
||
classes: ['fsUser']
|
||
associated_relations: ['primaryGroup', 'secondaryGroups']
|
||
relations:
|
||
primaryGroup:
|
||
type: belongs_to
|
||
object: group
|
||
foreign_key: gidNumber
|
||
primary_key: gidNumber
|
||
secondaryGroups:
|
||
type: belongs_to
|
||
object: group
|
||
many: uniqueMember
|
||
primary_key: dn
|
||
plugin:
|
||
min_uid: 10000
|
||
max_uid: 65535
|
||
step_uid: 100
|
||
default_group: dc-users
|
||
default_home_base: '/home'
|
conf/ldap_shadows/worlds/MilkyPond/shadows/Administration/aspects/ftp.conf | ||
---|---|---|
---
|
||
mapping:
|
||
classes: ['ftpUser']
|
||
depend_aspects: ['primary_account', 'fs']
|
conf/ldap_shadows/worlds/MilkyPond/shadows/Administration/aspects/jabber.conf | ||
---|---|---|
---
|
||
mapping:
|
||
classes: ['jabberUser']
|
conf/ldap_shadows/worlds/MilkyPond/shadows/Administration/aspects/mail.conf | ||
---|---|---|
---
|
||
mapping:
|
||
classes: ['emailUser']
|
conf/ldap_shadows/worlds/MilkyPond/shadows/Administration/aspects/primary_account.conf | ||
---|---|---|
---
|
||
mapping:
|
||
classes: ['primaryAccount']
|
||
associated_attributes: ['uid', 'allowedServices']
|
conf/ldap_shadows/worlds/MilkyPond/shadows/Administration/aspects/shell.conf | ||
---|---|---|
---
|
||
mapping:
|
||
classes: ['shellUser']
|
||
depend_aspects: ['primary_account', 'fs']
|
||
associated_attributes: ['loginShell']
|
conf/ldap_shadows/worlds/MilkyPond/shadows/Administration/aspects/web.conf | ||
---|---|---|
---
|
||
mapping:
|
||
classes: ['webUser']
|
||
depend_aspects: ['primary_account']
|
conf/ldap_shadows/worlds/MilkyPond/shadows/Administration/objects/bot.conf | ||
---|---|---|
---
|
||
mapping:
|
||
dn_attribute: uid
|
||
prefix: ''
|
||
classes: ['bot']
|
||
sort_by: uid
|
||
possible_aspects: ['primary_account', 'mail', 'fs', 'shell', 'ftp', 'web', 'jabber']
|
||
default_parent: "unit/SpecialAccounts"
|
||
presentation:
|
||
hidden_attributes: ['uid']
|
||
expert_attributes: ['uidNumber', 'gidNumber', 'gecos']
|
conf/ldap_shadows/worlds/MilkyPond/shadows/Administration/objects/domain.conf | ||
---|---|---|
---
|
||
mapping:
|
||
dn_attribute: cn
|
||
prefix: ''
|
||
classes: ['genericDomain']
|
||
sort_by: cn
|
||
parent_handle_restrictions: "^(unit/Domains|(individual|bot)/.+)$"
|
||
default_parent: "unit/Domains"
|
||
|
conf/ldap_shadows/worlds/MilkyPond/shadows/Administration/objects/entity.conf | ||
---|---|---|
---
|
||
mapping:
|
||
dn_attribute: o
|
||
prefix: ''
|
||
classes: ['entity']
|
||
excluded_classes: ['dcObject']
|
||
sort_by: o
|
||
associated_relations: ['foundersIndividuals', 'foundersEntities']
|
||
parent_handle_restrictions: "^unit/Entities$"
|
||
default_parent: "unit/Entities"
|
||
presentation:
|
||
name_attribute: o
|
||
hidden_attributes: ['founder']
|
||
relations:
|
||
foundersIndividuals:
|
||
type: has_many
|
||
object: individual
|
||
foreign_key: founder
|
||
primary_key: dn
|
||
foundersEntities:
|
||
type: has_many
|
||
object: entity
|
||
foreign_key: founder
|
||
primary_key: dn
|
conf/ldap_shadows/worlds/MilkyPond/shadows/Administration/objects/group.conf | ||
---|---|---|
---
|
||
mapping:
|
||
dn_attribute: cn
|
||
prefix: ''
|
||
classes: ['posixGroup', 'groupOfMembers']
|
||
sort_by: cn
|
||
associated_relations: ['individualsPrimaryMembers', 'botsPrimaryMembers', 'individualsSecondaryMembers', 'botsSecondaryMembers']
|
||
presentation:
|
||
hidden_attributes: ['uniqueMember']
|
||
expert_attributes: ['gidNumber']
|
||
relations:
|
||
individualsPrimaryMembers:
|
||
type: belongs_to
|
||
object: individual
|
||
many: gidNumber
|
||
primary_key: gidNumber
|
||
botsPrimaryMembers:
|
||
type: belongs_to
|
||
object: bot
|
||
many: gidNumber
|
||
primary_key: gidNumber
|
||
individualsSecondaryMembers:
|
||
type: has_many
|
||
object: individual
|
||
foreign_key: uniqueMember
|
||
primary_key: dn
|
||
botsSecondaryMembers:
|
||
type: has_many
|
||
object: bot
|
||
foreign_key: uniqueMember
|
||
primary_key: dn
|
conf/ldap_shadows/worlds/MilkyPond/shadows/Administration/objects/individual.conf | ||
---|---|---|
---
|
||
mapping:
|
||
dn_attribute: uid
|
||
prefix: ''
|
||
classes: ['individual']
|
||
sort_by: uid
|
||
possible_aspects: ['primary_account', 'mail', 'fs', 'shell', 'ftp', 'web', 'jabber']
|
||
parent_handle_restrictions: "^unit/People$"
|
||
default_parent: "unit/People"
|
||
presentation:
|
||
hidden_attributes: ['uid']
|
||
expert_attributes: ['uidNumber', 'gidNumber', 'gecos']
|
conf/ldap_shadows/worlds/MilkyPond/shadows/Administration/objects/secondary_account.conf | ||
---|---|---|
---
|
||
mapping:
|
||
dn_attribute: uid
|
||
prefix: ''
|
||
classes: ['secondaryAccount']
|
||
sort_by: uid
|
||
possible_aspects: ['mail', 'fs', 'shell', 'ftp', 'web', 'jabber']
|
||
parent_handle_restrictions: "^(unit/SpecialAccounts|(individual|bot|domain)/.+)$"
|
||
default_parent: "unit/SpecialAccounts"
|
||
associated_attributes: ['uid', 'allowedServices']
|
conf/ldap_shadows/worlds/MilkyPond/shadows/Administration/objects/system_account.conf | ||
---|---|---|
---
|
||
mapping:
|
||
dn_attribute: uid
|
||
prefix: ''
|
||
classes: ['systemAccount']
|
||
sort_by: uid
|
||
possible_aspects: ['mail', 'fs', 'shell', 'ftp', 'web', 'jabber']
|
||
default_parent: "unit/SpecialAccounts"
|
||
associated_attributes: ['uid', 'allowedServices']
|
conf/ldap_shadows/worlds/MilkyPond/shadows/Administration/objects/top_entity.conf | ||
---|---|---|
---
|
||
mapping:
|
||
dn_attribute: dc
|
||
prefix: ''
|
||
classes: ['entity', 'dcObject']
|
||
sort_by: o
|
||
parent_handle_restrictions: "^$"
|
||
presentation:
|
||
name_attribute: o
|
conf/ldap_shadows/worlds/MilkyPond/shadows/Administration/objects/unit.conf | ||
---|---|---|
---
|
||
mapping:
|
||
dn_attribute: ou
|
||
prefix: ''
|
||
classes: ['organizationalUnit']
|
||
# no sort_by means sort by DN
|
||
presentation:
|
||
name_attribute: dn
|
conf/ldap_shadows/worlds/MilkyPond/shadows/Administration/objects/user_service.conf | ||
---|---|---|
---
|
||
mapping:
|
||
dn_attribute: cn
|
||
prefix: ''
|
||
classes: ['userService']
|
||
sort_by: cn
|
||
possible_aspects: []
|
||
parent_handle_restrictions: "^unit/ProvidedServices$"
|
conf/ldap_shadows/worlds/MilkyPond/shadows/Administration/plugins/aspects/fs.rb | ||
---|---|---|
|
||
def self.hook_before_create(item)
|
||
hook_common(item)
|
||
end
|
||
|
||
def self.hook_before_modify(item)
|
||
hook_common(item)
|
||
end
|
||
|
||
def self.hook_common(item)
|
||
pconfig_default = {
|
||
:default_group => 'users',
|
||
:min_uid => 1000,
|
||
:max_uid => 65535,
|
||
:step_uid => 100,
|
||
:default_home_base => "/home"
|
||
}
|
||
pconfig = pconfig_default.merge(self.parameters[:plugin])
|
||
|
||
unless item.attribute_present?('gidNumber')
|
||
item.primaryGroup = item.class.shadow.get_object(:group).find(:first, pconfig[:default_group])
|
||
end
|
||
|
||
if item.attribute_present?('uidNumber')
|
||
user = ActiveLdap::Base.find(:first, :scope => :sub, :filter => "(&(objectClass=posixAccount)(uidNumber=#{item.uidNumber}))", :attributes => ['uidNumber'])
|
||
unless user.nil? or user.dn == item.dn
|
||
raise_error "UID already used by another item"
|
||
end
|
||
else
|
||
users = ActiveLdap::Base.find(:all, :scope => :sub, :filter => "(&(objectClass=posixAccount)(uidNumber=*))", :attributes => ['uidNumber'])
|
||
uidnumbers = users.collect {|user| user.uidNumber }
|
||
|
||
avail_uidnumber = nil
|
||
min_uidn = pconfig[:min_uid]
|
||
max_uidn = [min_uidn + pconfig[:step_uid], pconfig[:max_uid]].min
|
||
while avail_uidnumber.nil?
|
||
avail = (min_uidn..max_uidn).to_a - uidnumbers
|
||
unless avail.empty?
|
||
avail_uidnumber = avail.first
|
||
break
|
||
end
|
||
min_uidn = max_uidn
|
||
max_uidn = [min_uidn + pconfig[:step_uid], pconfig[:max_uid]].min
|
||
end
|
||
|
||
if avail_uidnumber.nil?
|
||
raise_error "Available UID range is depleted."
|
||
else
|
||
item.uidNumber = avail_uidnumber
|
||
end
|
||
end
|
||
|
||
unless item.attribute_present?('homeDirectory')
|
||
item.homeDirectory = File.join(pconfig[:default_home_base], item.uid)
|
||
end
|
||
end
|
conf/ldap_shadows/worlds/MilkyPond/shadows/Administration/plugins/aspects/primary_account.rb | ||
---|---|---|
|
||
require 'shared_attributes'
|
||
|
||
def self.hook_before_create(item)
|
||
hook_common(item)
|
||
end
|
||
|
||
def self.hook_before_modify(item)
|
||
hook_common(item)
|
||
end
|
||
|
||
def self.hook_common(item)
|
||
SharedAttr.check_common_attributes(item)
|
||
end
|
||
|
conf/ldap_shadows/worlds/MilkyPond/shadows/Administration/plugins/includes/shared_attributes.rb | ||
---|---|---|
module SharedAttr
|
||
module_function
|
||
|
||
def check_common_attributes(item)
|
||
if item.attribute_present?('allowedServices')
|
||
user_services = ActiveLdap::Base.find(:all, :scope => :sub, :filter => "(objectClass=userService)", :attributes => ['cn'])
|
||
srv_names = user_services.collect {|srv| srv.cn }
|
||
|
||
invalid_srv_names = item.allowedServices(true) - (item.allowedServices(true) & srv_names)
|
||
unless invalid_srv_names.empty?
|
||
raise PreProcessingError, "Invalid User Service(s) name(s): " + invalid_srv_names.join(", ")
|
||
end
|
||
end
|
||
end
|
||
end
|
conf/ldap_shadows/worlds/MilkyPond/shadows/Administration/plugins/objects/individual.rb | ||
---|---|---|
|
||
def self.hook_before_create(item)
|
||
unless item.attribute_present?('cn')
|
||
cn = item.surname || ""
|
||
cn = item.givenName + " " + cn if item.givenName
|
||
item.cn = cn
|
||
end
|
||
end
|
||
|
conf/ldap_shadows/worlds/MilkyPond/shadows/Administration/plugins/objects/secondary_account.rb | ||
---|---|---|
|
||
require 'shared_attributes'
|
||
|
||
def self.hook_before_create(item)
|
||
hook_common(item)
|
||
end
|
||
|
||
def self.hook_before_modify(item)
|
||
hook_common(item)
|
||
end
|
||
|
||
def self.hook_common(item)
|
||
SharedAttr.check_common_attributes(item)
|
||
end
|
||
|
conf/ldap_shadows/worlds/MilkyPond/shadows/Administration/plugins/objects/system_account.rb | ||
---|---|---|
|
||
require 'shared_attributes'
|
||
|
||
def self.hook_before_create(item)
|
||
hook_common(item)
|
||
end
|
||
|
||
def self.hook_before_modify(item)
|
||
hook_common(item)
|
||
end
|
||
|
||
def self.hook_common(item)
|
||
SharedAttr.check_common_attributes(item)
|
||
end
|
||
|
conf/ldap_shadows/worlds/MilkyPond/shadows/Administration/shadow.conf | ||
---|---|---|
---
|
||
presentation:
|
||
hidden_attributes: ['objectClass', 'userPassword', 'hasSubordinates', 'entryUUID', 'entryDN', 'structuralObjectClass', 'subschemaSubentry']
|
||
tree_objects: ['unit', 'entity']
|
conf/ldap_shadows/worlds/MilkyPond/shadows/Administration/translations/en.yml | ||
---|---|---|
---
|
||
en:
|
||
objects:
|
||
bot: "Bot"
|
||
domain: "Domain"
|
||
entity: "Entity"
|
||
group: "Group"
|
||
individual: "Individual"
|
||
secondary_account: "Secondary Account"
|
||
system_account: "System Account"
|
||
unit: "Unit"
|
||
user_service: "User Service"
|
||
attribute_types:
|
||
allowGlobalDirectory: "Disclose Own Contact Information in GLobal Directory"
|
||
cn: "Full Name"
|
||
createTimestamp: "Item creation time"
|
||
creatorsName: "Item Creator"
|
||
birthday: "Birthday"
|
||
birthlocation: "Birth Location"
|
||
description: "Description"
|
||
entryUUID: "Item UUID"
|
||
foundingDate: "Founding Date"
|
||
ftpHost: "FTP Allowed Hosts"
|
||
gecos: "GECOS"
|
||
gidNumber: "Primary Group (numeric)"
|
||
givenName: "FirstName"
|
||
homeDirectory: "Home Directory"
|
||
homePostalAddress: "Home Postal Address"
|
||
host: "Shell Allowed Hosts"
|
||
ipServiceName: "Service Name"
|
||
ipServiceHost: "Service Host"
|
||
ipServicePort: "Service Port"
|
||
ipServiceProtocol: "Service Protocol"
|
||
jid: "Jabber ID"
|
||
jpegPhoto: "Photo"
|
||
keyFingerPrint: "GPG/PGP Key Fingerprint"
|
||
labeledURI: "Web Site"
|
||
loginShell: "Shell Interpreter"
|
||
mail: "eMail address(es)"
|
||
mailForward: "eMail Forward Adress(es)"
|
||
mailQuota: "Maximum Mailbox Size"
|
||
manager: "Manager(s)"
|
||
mobile: "Mobile Phone"
|
||
modifiersName: "Item Last Modifier"
|
||
modifyTimestamp: "Item Last Modification Time"
|
||
occupation: "Job / Studies"
|
||
o: "Organization(s)"
|
||
structuralObjectClass: "Item Structural Classes"
|
||
owner: "Owner(s)"
|
||
preferredLanguage: "Language Preference"
|
||
sn: "Surname"
|
||
sshAuthKey: "SSH Public Key(s)"
|
||
uid: "Identifier (Login)"
|
||
uidNumber: "Identifier (numeric)"
|
||
uniqueAbbreviation: "Unique Abbreviation"
|
||
uniqueMember: "Group member"
|
||
userPassword: "Password"
|
||
webVirtualHost: "Hosted Web Sites"
|
||
allowedServices: "Authorized services"
|
||
relations:
|
||
primaryGroup: "Primary Group"
|
||
secondaryGroups: "Secondary Groups"
|
||
individualsPrimaryMembers: "Primary Member(s) Individual(s)"
|
||
botsPrimaryMembers: "Primary Member(s) Bot(s)"
|
||
individualsSecondaryMembers: "Secondary Member(s) Individual(s)"
|
||
botsSecondaryMembers: "Secondary Member(s) Bot(s)"
|
||
foundersIndividuals: "Founder(s) Individual(s)"
|
||
foundersEntities: "Founder(s) Entity(ies)"
|
||
aspects:
|
||
fs: "FileSystem Account"
|
||
ftp: "FTP Account"
|
||
jabber: "Jabber Account"
|
||
mail: "eMail Account"
|
||
primary_account: "Primary Account"
|
||
shell: "Shell Account"
|
||
web: "Web Account"
|
conf/ldap_shadows/worlds/MilkyPond/world.conf | ||
---|---|---|
---
|
||
default_shadow: Administration
|
||
password_hash: ssha
|
data/ldap_shadows/default_config/global.yaml | ||
---|---|---|
---
|
||
default_shadow:
|
||
password_hash:
|
||
ldap: {}
|
||
default_world:
|
data/ldap_shadows/default_config/world.yaml | ||
---|---|---|
---
|
||
default_shadow:
|
||
password_hash:
|
||
ldap: {}
|
data/ldap_shadows/schema/global.yaml | ||
---|---|---|
---
|
||
type: map
|
||
mapping:
|
||
"default_shadow": {type: str}
|
||
"ldap":
|
||
type: map
|
||
required: true
|
||
name: LdapMapping
|
||
mapping:
|
||
=:
|
||
type: any
|
||
"password_hash": {type: str, enum: [crypt, md5, smd5, sha, ssha]}
|
||
"default_world": {type: str}
|
||
|
data/ldap_shadows/schema/world.yaml | ||
---|---|---|
---
|
||
type: map
|
||
mapping:
|
||
"default_shadow": {type: str}
|
||
"ldap":
|
||
type: map
|
||
required: true
|
||
name: LdapMapping
|
||
mapping:
|
||
=:
|
||
type: any
|
||
"password_hash": {type: str, enum: [crypt, md5, smd5, sha, ssha]}
|
||
|
lib/ldap_shadows/config.rb | ||
---|---|---|
|
||
def initialize
|
||
@global_config = nil
|
||
@world_config = nil
|
||
@schemas = {}
|
||
@default_configs = {}
|
||
@shadows = {}
|
||
end
|
||
|
||
def load_global_config(extra_private_config_list = [])
|
||
def load_global_config
|
||
g_default_config = load_default_config('global')
|
||
|
||
g_config_file = File.join(CFG_DIR, "global.conf")
|
||
... | ... | |
end
|
||
|
||
g_def_partial = YAML.load_file(g_config_file) || {}
|
||
g_def = parse('config', 'global', YAML.dump(g_def_partial))
|
||
g_config = g_default_config.recursive_merge(g_def)
|
||
|
||
@global_config = g_config
|
||
end
|
||
|
||
def load_world_config(world_name = nil, extra_private_config_list = [])
|
||
world_name = self.global_config[:default_world] if world_name.nil?
|
||
|
||
w_default_config = load_default_config('world')
|
||
|
||
w_config_path = File.join(CFG_DIR, "worlds", world_name)
|
||
|
||
w_config_file = File.join(w_config_path, "world.conf")
|
||
unless File.exists? w_config_file
|
||
raise PreProcessingError, _("General configuration file for World '%s' is missing") % world_name
|
||
end
|
||
|
||
w_def_partial = YAML.load_file(w_config_file) || {}
|
||
extra_private_config_list += [
|
||
File.join(CFG_DIR, "global_private.conf")
|
||
File.join(w_config_path, "world_private.conf")
|
||
]
|
||
extra_private_config_list.each do |file|
|
||
if File.exists?(file)
|
||
g_def_partial.merge!(YAML.load_file(file) || {})
|
||
w_def_partial.merge!(YAML.load_file(file) || {})
|
||
break
|
||
end
|
||
end
|
||
g_def = parse('config', 'global', YAML.dump(g_def_partial))
|
||
g_config = g_default_config.recursive_merge(g_def)
|
||
w_def = parse('config', 'world', YAML.dump(w_def_partial))
|
||
w_config = w_default_config.recursive_merge(w_def)
|
||
|
||
ActiveLdap::Base.setup_connection(g_config[:ldap])
|
||
ActiveLdap::Base.setup_connection(w_config[:ldap])
|
||
|
||
@global_config = g_config
|
||
@world_config = w_config
|
||
@world_config_path = w_config_path
|
||
end
|
||
|
||
def global_config
|
||
... | ... | |
@global_config
|
||
end
|
||
|
||
def world_config
|
||
load_world_config() if @world_config.nil?
|
||
@world_config
|
||
end
|
||
|
||
# needs 'ldap_shadows/shadow' for this feature to work
|
||
def load_shadow(shadow_name = nil)
|
||
shadow_name = self.global_config[:default_shadow] if shadow_name.nil?
|
||
shadow_name = self.world_config[:default_shadow] if shadow_name.nil?
|
||
if shadow_name.nil?
|
||
raise PreProcessingError, _("Could not determine which Shadow to travel through")
|
||
end
|
||
|
||
shadow_config_path = File.join(CFG_DIR, "shadows", shadow_name)
|
||
shadow_config_path = File.join(@world_config_path, "shadows", shadow_name)
|
||
unless File.exists? shadow_config_path
|
||
raise PreProcessingError, _("Configuration directory for Shadow '%s' is missing") % shadow_name
|
||
end
|
||
... | ... | |
|
||
if validate
|
||
validator_klass = case type
|
||
when 'global'
|
||
GlobalValidator
|
||
when 'world'
|
||
WorldValidator
|
||
when 'object'
|
||
ObjectValidator
|
||
when 'aspect'
|
||
... | ... | |
end
|
||
end
|
||
|
||
class GlobalValidator < LdapShadowsValidator
|
||
class WorldValidator < LdapShadowsValidator
|
||
def validate_hook_in(value, rule, path, msg_list)
|
||
case rule.name
|
||
when 'LdapMapping'
|
Also available in: Unified diff
[evol] added support for multiple worlds (closes #144)