#!/usr/bin/env ruby require 'toml' require 'net/ldap' @configuration_file = "/etc/unipoly-mlmmj-ldap-sync.toml" def read_configuration(path) TOML.load_file(path) end def connect_ldap(conf) conn = Net::LDAP.new( :host => conf["ldap"]["host"], :port => conf["ldap"]["port"], :auth => { :method => :simple, :username => conf["ldap"]["auth"]["username"], :password => conf["ldap"]["auth"]["password"] }) begin if conn.bind conn else puts "Failed to authenticate against LDAP server: \ #{conf["ldap"]["host"]}:#{conf["ldap"]["port"]}" exit(1) end rescue puts "Failed to contact LDAP server: \ #{conf["ldap"]["host"]}:#{conf["ldap"]["port"]}" exit(1) end end def main conf = read_configuration(@configuration_file) conn = connect_ldap(conf) domain = conf["domain"] basetree = conf["ldap"]["lists"]["basetree"] lists = (conf["lists_add"] + conf["lists_remove"]).uniq lists.each do |cn| puts ">> Processing list #{cn}@#{domain}" filter = Net::LDAP::Filter.eq("cn", cn) print "Searching LDAP... " match = conn.search(:base => basetree, :filter => filter) if (match.size > 0) entry = match.first members = entry.uniquemember.map do |dn| /mail=([^,]+),/.match(dn).values_at(1).first.downcase end puts "OK" puts "Found #{entry.dn} with #{members.size} members" print "Searchin mlmmj... " mlmmj_list_binary = conf["mlmmj"]["list_binary"] mlmmj_basepath = conf["mlmmj"]["basepath"] list = "#{mlmmj_basepath}/#{cn}@#{domain}" if (File.executable?(mlmmj_list_binary)) raw = %x(#{mlmmj_list_binary} -L #{list} -s) if ($?.exitstatus == 0) puts "OK" subscribers = raw.split("\n") puts "Found #{cn}@#{domain} with #{subscribers.size} subscribers" print "\n" # Add to the subscribers any missing entry # Remove successful matches members.each do |m| if (subscribers.include?(m)) subscribers.delete(m) else if (conf["lists_add"].include?(cn)) print "Adding #{m}... " mlmmj_sub_binary = conf["mlmmj"]["sub_binary"] %x(#{mlmmj_sub_binary} -L #{list} -a #{m} -q -f -s) if ($?.exitstatus == 0) puts "OK" else puts "Failed" end end end end # Remove remaining "subcribers" (= they did not match with members) if (conf["lists_remove"].include?(cn)) subscribers.each do |s| print "Removing #{s}... " mlmmj_unsub_binary = conf["mlmmj"]["unsub_binary"] %x(#{mlmmj_unsub_binary} -L #{list} -a #{s} -q -s) if ($?.exitstatus == 0) puts "OK" else puts "Failed" end end end print "\n" else puts "FAIL" end else puts "could not execute #{mlmmj_list_binary}" end else puts "FAIL" end end end main()