Ключевые слова:qmail, mail, ldap, (найти похожие документы)
From: nikll <nikll@rambler.ru.>
Newsgroups: email
Date: Mon, 2 Oct 2010 17:02:14 +0000 (UTC)
Subject: Интеграция qmail и Active Directory
1. Подгатовка, анализ, изучение задачи
Была задача сделать новый шлюз для компании с локалкой на 150 компов, у
них был 2003 домен, старый шлюз работал кое как был поднят на фре 6.0
несколько лет назад, путем анализа того что там было наворочено
выяснелось следущее:
Сначала на нем делали sendmail+sasl, потом пробовали qmail+vpopmail,
затем exim, и в итоге во всю эту кашу воткнули postfix (да кстати они
все это из исходников руками собирали... неудаляя старое... в итоге
хвостов осталось....), в общем погледев на эти джедайства пришел к
выводу что прощще сделать заного чем разбирать весь этот лес.
Подумав я решил взять кумейл за основу (с ним у меня уже был
положительный опыт но на мускуле), т.к. у компании есть 2003 домен, а
админы виндовые, решил завязать все это на домен.
В итоге схема вырисовывается такая:
При заведении нового пользователя в АД, в доп поля учетки заносятся
почтовый адрес, алдиасы, форварды и квоты, когда ползователь первый раз
подключается к почтарю, кумейл подключаетсья к MS_LDAP, находит юзера по
полю "sAMAccountName" (это логин в АД), смотрит его настройки, и пробует
переподключиться к лдапу с его логином и паролем, если это получается
новому юзеру автоматически создается его почтовый каталог (Mailbox).
Путем проб и ошибок убедился что необходимости править схему АД нет, как
нет и необходимости в установе SFU (Microsoft Unix Servises, nis nfs
x11 и прочее).
2. Что за зверь LDAP, и как его готовить чтобы было вкусно...
Раньше я только слышал как все говорят лдап лдап, сам же я неимел
практического опыта в этой сфере, было решино устранять пробелы в
знаниях :).
Установил из портов /usr/ports/net/openldap23-client, и создал в корне
АД учетку ldapadmin с правами админа (группы "Domain Admins, Enterprise
Admins, Schema Admins") для работы с лдап.
Потом настроил лдап клиент:ee /usr/local/etc/openldap/ldap.conf
BASE dc=<ваш>, dc=<домен>
URI ldap://dc1.<ваш>.<домен> ldap://dc2.<ваш>.<домен>
Проверяем работу с MS_LDAP:ldapsearch -w 123456789 -D cn=ldapadmin,dc=uc,dc=local sAMAccountName=kotlyarov
# extended LDIF
#
# LDAPv3
# base <> with scope subtree
# filter: sAMAccountName=kotlyarov
# requesting: ALL
#
# \D0\9A\D0\BE\D1\82\D0\BB\D1\8F\D1\80\D0\BE\D0\B2 \D0\9D\D0\B8\D0\BA\D0\BE\D
0\BB\D0\B0\D0\B9 \D0\9D\D0\B8\D0\BA\D0\BE\D0\BB\D0\B0\D0\B5\D0\B2\D0\B8\D1\8
7, \D0\91\D1\8E\D1\80\D0\BE \D0\9F\D1\80\D0\BE\D0\B3\D1\80\D0\B0\D0\BC\D0\BC
\D0\B8\D1\80\D0\BE\D0\B2\D0\B0\D0\BD\D0\BD\D0\B8\D1\8F, \D0\9F\D0\BE\D0\BB\D
1\8C\D0\B7\D0\BE\D0\B2\D0\B0\D1\82\D0\B5\D0\BB\D0\B8, UC.local
dn:: Q0490JrQvtGC0LvRj9GA0L7QsiDQndC40LrQvtC70LDQuSDQndC40LrQvtC70LDQtdCy0LjRh
yxPVT3QkdGO0YDQviDQn9GA0L7Qs9GA0LDQvNC80LjRgNC+0LLQsNC90L3QuNGPLE9VPdCf0L7Qu9
GM0LfQvtCy0LDRgtC10LvQuCxEQz1VQyxEQz1sb2NhbA==
objectClass: top
objectClass: person
objectClass: organizationalPerson
objectClass: user
cn:: 0JrQvtGC0LvRj9GA0L7QsiDQndC40LrQvtC70LDQuSDQndC40LrQvtC70LDQtdCy0LjRhw==
sn:: 0JrQvtGC0LvRj9GA0L7Qsg==
l: 500000000
st: 5000
title:: 0J/RgNC+0LPRgNCw0LzQvNC40YHRgg==
physicalDeliveryOfficeName:: 0JHRjtGA0L4g0J/RgNC+0LPRgNCw0LzQvNC40YDQvtCy0LDQvdC90LjRjw==
telephoneNumber: 598
givenName:: 0J3QuNC60L7Qu9Cw0Lk=
distinguishedName:: Q0490JrQvtGC0LvRj9GA0L7QsiDQndC40LrQvtC70LDQuSDQndC40LrQvt
C70LDQtdCy0LjRhyxPVT3QkdGO0YDQviDQn9GA0L7Qs9GA0LDQvNC80LjRgNC+0LLQsNC90L3QuNG
PLE9VPdCf0L7Qu9GM0LfQvtCy0LDRgtC10LvQuCxEQz1VQyxEQz1sb2NhbA==
instanceType: 4
whenCreated: 20080324190217.0Z
whenChanged: 20080415111135.0Z
displayName:: 0JrQvtGC0LvRj9GA0L7QsiDQndC40LrQvtC70LDQuSDQndC40LrQvtC70LDQtdCy0LjRhw==
otherTelephone: sysadmin@*****.**
otherTelephone: programist@*****.ru
otherTelephone: administrator@*****.ru
otherTelephone: admin@*****.ru
otherTelephone: nikll@*****.ru
uSNCreated: 56181
memberOf: CN=unix_admins,CN=Users,DC=UC,DC=local
memberOf: CN=folder_redirection,CN=Users,DC=UC,DC=local
memberOf: CN=Schema Admins,CN=Users,DC=UC,DC=local
memberOf: CN=Enterprise Admins,CN=Users,DC=UC,DC=local
uSNChanged: 145216
name:: 0JrQvtGC0LvRj9GA0L7QsiDQndC40LrQvtC70LDQuSDQndC40LrQvtC70LDQtdCy0LjRhw= =
objectGUID:: Os9FCrXab0uQPmiLxcQC+Q==
userAccountControl: 66048
badPwdCount: 0
codePage: 0
countryCode: 0
badPasswordTime: 128527239789843750
lastLogoff: 0
lastLogon: 128527314918750000
pwdLastSet: 128521200854000482
primaryGroupID: 512
objectSid:: AQUAAAAAAAUVAAAApvsbRyTqxJDX0hZPUgYAAA==
adminCount: 1
accountExpires: 9223372036854775807
logonCount: 346
sAMAccountName: kotlyarov
sAMAccountType: 805306368
managedObjects: CN=dfs,CN=Dfs-Configuration,CN=System,DC=UC,DC=local
managedObjects:: Q049QlVIMDAsT1U90JHRg9GF0LPQsNC70YLQtdGA0LjRjyxPVT3QmtC+0LzQv
9GM0Y7RgtC10YDRiyxEQz1VQyxEQz1sb2NhbA==
managedObjects:: Q049VFMyLE9VPdCh0LXRgNCy0LXRgNCwLE9VPdCa0L7QvNC/0YzRjtGC0LXRg
NGLLERDPVVDLERDPWxvY2Fs
managedObjects:: Q049VFMxLE9VPdCh0LXRgNCy0LXRgNCwLE9VPdCa0L7QvNC/0YzRjtGC0LXRg
NGLLERDPVVDLERDPWxvY2Fs
managedObjects: CN=DC1,OU=Domain Controllers,DC=UC,DC=local
managedObjects: CN=DC2,OU=Domain Controllers,DC=UC,DC=local
managedObjects: DC=UC,DC=local
userPrincipalName: kotlyarov@UC.local
url: nikll@rambler.ru
servicePrincipalName: MSSQLSvc/DC1.uc.local:1433
servicePrincipalName: MSSQLSvc/DC2.UC.local:1433
objectCategory: CN=Person,CN=Schema,CN=Configuration,DC=UC,DC=local
dSCorePropagationData: 20080408094349.0Z
dSCorePropagationData: 20080408094349.0Z
dSCorePropagationData: 20080408094349.0Z
dSCorePropagationData: 20080408085453.0Z
dSCorePropagationData: 16010108151056.0Z
lastLogonTimestamp: 128527070442343750
mail: kotlyarov@*****.ru
# search reference
ref: ldap://ForestDnsZones.UC.local/DC=ForestDnsZones,DC=UC,DC=local
# search reference
ref: ldap://DomainDnsZones.UC.local/DC=DomainDnsZones,DC=UC,DC=local
# search reference
ref: ldap://TAPI3Directory.UC.local/DC=TAPI3Directory,DC=UC,DC=local
# search reference
ref: ldap://UC.local/CN=Configuration,DC=UC,DC=local
# search result
search: 2
result: 0 Success
# numResponses: 6
# numEntries: 1
# numReferences: 4
Ага значит работает :))))
Коментарии:
ldapsearch - Программа для поиска в лдап
-w 123456789 - пароль к учетной записи
-D cn=ldapadmin,dc=uc,dc=local - собственно учетка от имени которой мы подключаемя
sAMAccountName=kotlyarov - тип обьекта и его значение
Обьекты в LDAP бывают следующих типов:
dc: - корень лдап
cn: - контейнер (Папки Users Computers и учетные записи)
ou: - Organization Unit (типо папка к которой можно привязать политики)
l: - City (в свойствай учетки на влкадке Address) я использую для задания лимита в байтах
st: - State/Province (в свойствай учетки на влкадке Address) лимит в письмах
sAMAccountName: - логин
otherTelephone: - Кнопка Other.. на вкладке "Geniral" напротив поля "Telephone number:" у меня это почтовые алиасы
url: - Кнопка Other.. на вкладке "Geniral" напротив поля "Web page:" у меня это форварды
Можно поиграться например вот так:
посмотрим про админа домена
ldapsearch -w 123456789 -D cn=ldapadmin,dc=uc,dc=local sAMAccountName=Administrator
найдем и просмотрим всех у кого мыло admin@mu.domain
ldapsearch -w 123456789 -D cn=ldapadmin,dc=uc,dc=local mail=admin@mu.domain
подключимся к домену от имени админа, найдем и просмотрим всех у кого
форвард на qwerty@ramber.ru
ldapsearch -w asdfasezx -D cn=Administrator,cn=Users,dc=uc,dc=local url=qwerty@ramber.ru
3. Кумейл по джедайски, в соусе из AD.....
Идем в порты:cd /usr/ports/mail/qmail-ldap/
make config
у мна получилось следующее:
[nikll@gate1 qmail-ldap ]$ make showconfig
===> The following configuration options are available for qmail-ldap-1.03.20060201_1:
LOCALTIME_PATCH=on "emit dates in the local timezone"
TLS=on "SMTP TLS support"
ALTQUEUE=on "run a QMAILQUEUE external queue"
BIGBROTHER=off "use the control/bigbrother program"
BIGTODO=on "use big_todo qmail patch"
BIND_8_COMPAT=off "Needed if compile fails building dns.c"
CLEARTEXTPASSWD=off "use cleartext passwords (Dangerous!)"
DASH_EXT=on "dash_ext extended mail addresses add"
DATA_COMPRESS=on "smtp on the fly DATA compression"
EXTERNAL_TODO=on "external high-performance todo processing"
IGNOREVERISIGN=off "disallow dns wildchar matches on gtlds"
QLDAP_CLUSTER=on "cluster support"
QMQP_COMPRESS=on "QMQP on the fly compression"
QUOTATRASH=on "include the Trash in the quota"
SMTPEXECCHECK=on "smtp DOS/Windows executable detection"
AUTOMAILDIRMAKE=on "the auto-maildir-make feature"
AUTOHOMEDIRMAKE=on "auto-homedir-make feature"
LDAP_DEBUG=on "possibility to log and debug imap/pop"
SMTPEXTFORK=off "Allow qmail-smtpd fork external progs"
XF_QUITASAP=off "Close SMTP session ASAP (SMTPEXTFORK)"
QEXTRA=off "enable QUEUE_EXTRA copy feature"
===> Use 'make config' to modify these settings
делаемmake patch
cd work/qmail-1.03/
ee qmail-ldap.h
Проставляем нужные параметы, я поменял следующее:
diff -u2 -r qmail-ad/qmail-1.03/qmail-ldap.h work/qmail-1.03/qmail-ldap.h
--- qmail-ad/qmail-1.03/qmail-ldap.h 2008-04-13 13:23:03.000000000 +0600
+++ work/qmail-1.03/qmail-ldap.h 2008-04-13 13:31:26.000000000 +0600
@@ -42,5 +42,5 @@
/* triger level for quotawarning (0-100) */
-#define QUOTA_WARNING_LEVEL 90
+#define QUOTA_WARNING_LEVEL 70
/* reply subject for mails without subjects. */
@@ -94,14 +94,14 @@
*********************************************************************/
#define LDAP_MAIL "mail"
-#define LDAP_MAILALTERNATE "otherTelephone" /* Почтовые алиасы */
+#define LDAP_MAILALTERNATE "mailAlternateAddress"
#define LDAP_QMAILUID "qmailUID"
#define LDAP_QMAILGID "qmailGID"
-#define LDAP_MAILSTORE "sAMAccountName" /* Доменная учетка*./
-#define LDAP_HOMEDIR "NOhomeDirectory"
+#define LDAP_MAILSTORE "mailMessageStore"
+#define LDAP_HOMEDIR "homeDirectory"
#define LDAP_QUOTA "mailQuota"
-#define LDAP_QUOTA_SIZE "l" /* Размер Квоты в байтах */
-#define LDAP_QUOTA_COUNT "st" /* Размер квоты в письмах */
+#define LDAP_QUOTA_SIZE "mailQuotaSize"
+#define LDAP_QUOTA_COUNT "mailQuotaCount"
#define LDAP_MAXMSIZE "mailSizeMax"
-#define LDAP_FORWARDS "url" /* Форвардинг в другие почтовые ящщики */
+#define LDAP_FORWARDS "mailForwardingAddress"
#define LDAP_PROGRAM "deliveryProgramPath"
#define LDAP_MAILHOST "mailHost"
@@ -109,8 +109,8 @@
#define LDAP_REPLYTEXT "mailReplyText"
#define LDAP_DOTMODE "qmailDotMode"
-#define LDAP_UID "sAMAccountName" /* Поле по каоторому qmail авторизируется */
-#define LDAP_PASSWD "msSFU30Password"
+#define LDAP_UID "uid"
+#define LDAP_PASSWD "userPassword"
#define LDAP_OBJECTCLASS "objectClass"
-#define LDAP_ISACTIVE "userAccountControl"
+#define LDAP_ISACTIVE "accountStatus"
#define LDAP_PURGE "qmailAccountPurge"
@@ -133,9 +133,8 @@
#define MODE_NOREPLY "noreply"
-#define ISACTIVE_BOUNCE "514"
+#define ISACTIVE_BOUNCE "disabled"
#define ISACTIVE_DELETE "deleted"
#define ISACTIVE_NOACCESS "noaccess"
-#define ISACTIVE_ACTIVE "512"
-#define ISACTIVE_ACTIVE_AD "66048"
+#define ISACTIVE_ACTIVE "active"
потом правим файл qmail-ldaplookup.c
diff -u2 -r qmail-ad/qmail-1.03/qmail-ldaplookup.c work/qmail-1.03/qmail-ldaplookup.c
--- qmail-ad/qmail-1.03/qmail-ldaplookup.c 2008-04-11 19:27:39.000000000 +0600
+++ work/qmail-1.03/qmail-ldaplookup.c 2008-04-13 13:31:26.000000000 +0600
@@ -322,6 +322,6 @@
switch (status) {
case STATUS_BOUNCE:
- output(subfdout, "%s: %s %s\n",
- LDAP_ISACTIVE, ISACTIVE_BOUNCE, "=> disabled");
+ output(subfdout, "%s: %s\n",
+ LDAP_ISACTIVE, ISACTIVE_BOUNCE);
break;
case STATUS_NOACCESS:
@@ -330,6 +330,6 @@
break;
case STATUS_OK:
- output(subfdout, "%s: %s %s\n",
- LDAP_ISACTIVE, ISACTIVE_ACTIVE, "=>active");
+ output(subfdout, "%s: %s\n",
+ LDAP_ISACTIVE, ISACTIVE_ACTIVE);
break;
case STATUS_UNDEF:
это необходимо для того чтобы кумейл правильно распозновал отключенных
юзеров в АД ну вот и все вроде теперь можно устанавливатьcd ../..
make install clean
4. Тяжелые интимные отношения с авторизацией.
Долго ломал голову как проверять пароли у юзеров, изночально qmail-ldap
берет их из отельного поля в лдапе, криптует их сам, пробовал вариант с
изменением схемы АД чтобы у учеток было это поле, впринципе работает но
всеравно некрасиво, хочется чтобы пароль был единый и задавался через
mmc коснсоль.
Пгуглил маленько нашел упоминание про SFU и про то что через нее можно
сохранять qmail совместимый пароль прямо в обьектах учетки, поле
называетсо "msSFU30Password", но есть минусы, надо скачать ~300 метров с
сата мс, установить и настроить эту хрень на всех контроллерах домена,
активировать маппинг из winAD в unix у всех юзерских учеток и после
этого перезадать всем юзерам пароли чтобы у них заполнилось поле
"msSFU30Password", вдоволь поигравшись с этой байдой решил что это
далеко не самый лудший вариант.
Я пошел дальше и касковыряв исходники сначала научил кумейл проверять
пароль из обычного текстового поля без всякого криптования, получилось
что мы можем задавать пароль на почту средствами винды но темнемение он
задается отдельно от доменного и храниться в plain тексте некриптованный
что тоже не есть гут.
Пока ковырялся в исходниках меня понесло на программированние, в итоге
был напластан патч из 12 страниц для проверки пароля через вызов kinit
(kerberos), пока долизывал патч обнаружил в исходниках готовое и
красивое решение, которое заключалось в том чтобы просто
переподключаться к лдапу с именем и паролем юзера которого надо
проверить :). Для того чтобы это заработало надо только создать файл
ldaprebind и записать в него еденичку:echo 1 >
/var/qmail/control/ldaprebind
и все прекрастно заработает безовсяких керберосов и прочих извратов... :):):)
5. Циплята учатся летать... или базовая настройка qmail-ldap
Cоздаем системного юзера для работы с виртуальными почтовыми ящщиками и
прописываем его в кумейл:
pw groupadd vmail
pw useradd -n vmail -g virtmail -s /sbin/nologin
mkdir /shares/maildirs
echo "/shares/maildirs" > /var/qmail/control/ldapmessagestore
echo '#!/bin/bash' > /var/qmail/bin/dirmaker
echo 'mkdir -m 700 -p $1' >> /var/qmail/bin/dirmaker
echo "/var/qmail/bin/dirmaker" > /var/qmail/control/dirmaker
chown vmail:vmail /shares/maildirs /var/qmail/bin/dirmaker
chmod 700 /shares/maildirs
chmod 4755 /var/qmail/bin/dirmaker
awk -F: '/^vmail/ {print $3}' < /etc/passwd > /var/qmail/control/ldapuid
awk -F: '/^vmail/ {print $3}' < /etc/passwd > /var/qmail/control/ldapgid
Ну и собственно остальная конфигурация:
cd /var/qmail/control
echo "mail.mu.domain" > me # полное доменное имя (FQDN) почтового сервера
echo "mu.domain" >> rcpthosts # все имена (FQDN) доменов для которых
echo "mu2.domain" >> rcpthosts # мы должны принимать почту
echo "mu.domain" >> locals # имена (FQDN) доменов которым
echo "mu2.domain" >> locals # почта достовляеться локально
echo "dc=mu_local, dc=domain" > ldapbasedn # Ваш доменный лдап
echo "dc1.mu_local.domain dc2.mu_local.domain" > ldapserver # контролеры домена
echo "dn=ldapadmin, dc=mu_local, dc=domain" > ldaplogin # доменная админская учетка
echo "123456789" >ldappassword # Пароль учетки
chmod 600 ldappassword # защщищаем пароль от посторонних глаз
chown qmaild 600 ldappassword # и разрешаем кумейлу его читать
echo "0" > ldaplocaldelivery # если поставить в 1 то почту можно будет получать не только
# для доменных но и для системных юзеров
echo "1" > ldaprebind # самое главное, эх если бы я эту фичу с самого начала знал,
# скока бы времени и сил сэкономил, это собственно способ авторизации юзеров путем попытки
# подключения к лдапу от их имени
echo "both" > ldapdefaultdotmode # для того чтобы кумайл считывал как файы .qamil так и поля
# из АД "deliveryProgramPath"
echo "1000" > defaultquotacount # настройка дефолтной квоты для тех случаев если
echo "2000000" > defaultquotasize # мы ее непроставили в АД (количество писем и обьем
# ящщика в байтах)
echo "You have exceeded your quota!" > quotawarning # приписка в сообщения о переполнении квоты
echo "technical support +7 (343) 2326435" >> custombouncetext # приписка к отвергнутым (bounce) сообщениям
Про настройки tcpserver я рассказыать небуду, в интернете это достаточно
хороше описанно приведу только пример своих конфигов:
[nikll@gate1 control ]$ more qmail-imapd.rules
:allow,IMAP_CAPABILITY="IMAP4rev1 CHILDREN NAMESPACE THREAD=ORDEREDSUBJECT THREAD=REFERENCES SORT QUOTA",NOPBS="",LOGLEVEL="3"
[nikll@gate1 control ]$ more qmail-pop3d.rules
:allow,NOPBS="",LOGLEVEL="9"
[nikll@gate1 control ]$ more qmail-smtpd.rules
192.168.0.:allow,SENDERCHECK="",RELAYCLIENT="",NOPBS="",REJECTEXEC=""
112.112.110.:allow,SENDERCHECK="",RELAYCLIENT="",SMTPAUTH="",NOPBS="",REJECTEXEC=""
127.:allow,RCPTCHECK="",SENDERCHECK="",SMTPAUTH="",NOPBS="",REJECTEXEC=""
:allow,RCPTCHECK="",SENDERCHECK="",RETURNMXCHECK="",SANITYCHECK="",SMTPAUTH="",BLOCKRELAYPROBE="",REJECTEXEC="",RBL="",NOPBS=""
Сами файлы лежат в /var/qmail/conrtol/
файлы *.cdb создаються командой gmake выполненной в каталоге с конфигами
Ну вот вроде бы и все, осталось только запустить весь этот суп в полет, делаем:
echo 'sendmail_enable="NONE"' >> /etc/rc.conf
echo 'svscan_enable="YES"' >> /etc/rc.conf
/usr/local/etc/rc.d/svscan.sh restart
Поздравляю, кумейл поднят и запущщен, теперь можно потестировать это.
P.S. внимание антиспам ненастроен!!! сначала хотел сделать как обычно
(rbl+spamassassin), но в последний момент наткнулся на http://www.spamdyke.org/,
занятная штучка, в ней есть практически все :), кто ею пользовался пожалуйста отзовитесь.....
Наткнулся на упоминания о неком dspam, якобы тоже хорошая весч
(применяеться вместо spamassasin), тоже интересует опыт использованния
его с кумейлом
Ну и напоследок кто юзал simscan? я раньше делал через .pl скрипт
который вызывался вместо QMAILQEUE, а на сайте разработчиков qmail-ldap
рекомендуется именно simscan...