Ключевые слова:billing, radius, auth, aaa, sql, (найти похожие документы)
From: Асен Тотин <[email protected]>
Newsgroups: email
Date: Mon, 11 Sep 2003 14:31:37 +0000 (UTC)
Subject: Дизайн биллинг системы с использованием RADIUS и внешней верификации
Документ можно скачать в виде PDF по адресу: http://bilbo.online.bg/~assen/radius.pdf
ДИЗАЙН БИЛЛИНГ СИСТЕМы С ИСПОЛЬЗОВАНИЕМ RADIUS И ВНЕШНЕЙ ВЕРИФИКАЦИИ
ВВЕДЕНИЕ
RADIUS (Remote Authentication Dial-In User Srevice) - стандартный
прокотол для верификации потребителей, разработанный голландской
компанией Cistron. Протокол функционирует на базе диалога "клиент-сервер".
На сегодняшний ден практически все производители NAS (Network Access
Servers) имеют встроенную поддержку этого протокола (встроенный RADIUS
клиент). Посколько протокол общедоступен, существует множество
имплементаций сервера.
Исторически первым RADIUS сервером был Cistron RADIUS, хранящий всю
конфигурацию, а также информацию от сессиях клиентов в текстовых файлах.
В связи с развитием SQL как удобной платформы сохранения и обработки
данных, был создан патч для Cistron RADIUS, позволявший хранить данные в
SQL масиве. Неудобство заключается в том, что структура SQL массива
просто повторяет структуру текстовых файлов, не используя множество
удобств реляционных баз данных, предлагемые SQL.
Для использования полной мощи SQL требуется изменить структуру
информационного массива. Новая структура, в свою очередь, требует новых
средств для записи и извлечения данных, которыми Cistron RADIUS не
располагает.
XtRADIUS был разработан на базе кода Cistron RADIUS, но с одним отличием
- он использует внешнюю верификацию потребителей, что позволяет
содержать всю поступающюю информацию в удобном виде.
На нынешний день множество других имплементаций RADIUS сервера позволяют
проводить внешнюю верификацию.
ДИЗАЙН СТРУКТУРы
При испозовании внешней верификации коммуникация проходит следующим образом:
1. Потребитель сети подключается к ней (напр., модемом).
2. NAS устанавливает протокол связи (чаще всего - Point-to-point Protocol,
PPP), получает от потребителя его имя и пароль и передает их вместе со
своим ключом и идентификатором обмена указанному RADIUS серверу.
3. RADIUS сервер выделяет имя потребителя, его пароль, а также другие
аттрибуты связи (например, имя или IP адрес NAS) и подает их внешнему
слою дла верификации.
4. Слой верификации делает справку в информационном масиве SQL и
принимает решение верифицировать потребителя или нет. Сообщение
передается RADIUS серверу при помощи exit code. Если необходимо, перед
этим можно передать RADIUS серверу информацию для RADIUS-клиента.
5. В зависимости от решения верификационного слоя, RADIUS сервер дает
команду RADIUS клиенту о допуске или сбрасывании потребителя.
УСТАНОВКА RADIUS СЕРВЕРА
XtRADIUS можно скачать по следующему адресу: http://xtradius.sourceforge.com.
XtRADIUS устанавливается обычным для C программ способом:
./configure && make && make install.
Перед компиляцией не мешает проверить IP порты установки RADIUS - раньше
пользовались 1645 и 1646, с некоторого времени - 1812 и 1813. Сервер
может работать только на одной паре портов, для замены портов нужна
перекомпиляция. Сервер и клиент должны работать на одной и той же паре портов.
Конфигурация XtRADIUS находится в дирестории /etc/raddb. Ниже показана
конфигурация главных файлов для внешней верификации потребителей:
/etc/raddb/naslist - содержит список NAS
# NAS Name Short Name Type
#---------------- ---------- ----
nas1.somedomain.com nas1 other
nas2.somedomain.com nas2 other
nas3.somedomain.com nas3 other
/etc/raddb/naslist - содержит список ключей NAS
# Client Name Key
#---------------- ----------
nas1.somedomain.com Key1
nas2.somedomain.com Key2
nas3.somedomain.com Key3
N.B.: Каждый клиент должен знать свой ключ (Key).
/etc/raddb/users - содержит список RADIUS аттрибутов и их сокращенных
обозначений, которые можно подавать внешним программам при верификации:
# Used letters: a b c d e f g h i k n o p s t u w x y z
# Free letters: b j l m q r v
NAS-IP-Address n
Framed-MTU t
User-Name u
Password w
Callback-Number c
Framed-Protocol a
Acct-Session-Time e
Acct-Input-Octets i
Acct-Output-Octets o
NAS-Port-Type y
Acct-Status-Type d
Connect-Info s
Calling-Station-Id g
Called-Station-Id h
NAS-Port-Id p
Framed-IP-Address f
Acct-Terminate-Cause z
Acct-Session-Id b
/etc/raddb/execparams - содержит список внешних программ для верификации
и список параметров, подаваемых им. Слой для верификации использует два
типа RADIUS пакетов: Alive и Stop. Start пакет не используется по той
причине, что он не содержит в себе IP адрес, присвоенный потребителю.
Этот адрес приходит лишь в Alive пакете. Разница во времени двух
пакетов - не более нескольких секунд, что существенно на статистику потребителей
не влияет. При самой верификации потребителя пароль поставляется
внешнему слою не через command-line параметр, а через environment
variable. Это делается с целью избежания появления пароли в log файлах.
DEFAULT Acct-Status-Type = "Alive"
Exec-Program-Account = "/usr/local/bin/alive.pl %u %n %p %y %g %b %f"
DEFAULT Acct-Status-Type = "Stop"
Exec-Program-Account = "/usr/local/bin/stop.pl %u %n %p %i %o %z %e %b"
# The password is not supplied via %w any more,
# but via "User-Password" environment variable.
# Thus we avoid having it logged in plain text in radius.log.
DEFAULT Auth-Type = "External"
Service-Type = Framed-User,
Framed-Protocol = PPP,
Framed-Routing = Broadcast-Listen,
Framed-MTU = 1500,
Framed-Compression = Van-Jacobsen-TCP-IP,
Exec-Program-Wait = "/usr/local/bin/login.pl %u %n %p %y %g",
Fall-Through = Yes
SQL МАССИВ
Чтобы полностью воспользоваться возможностями SQL, информационный массив
был разработан в следующем виде:
- Таблица users, содержащяя информацию о потребителях: имя, пароль,
тип сервиса, последний день, когда клиенту разрешен доступ, остаточное
время (если у клиента prepaid сервис), а также другая информация -
напр., телефон и email для связи и т.д. Для каждого потребителя
делается одна запись в таблице.
- Таблица payments, содержащяя информацию о поступивших взносах
клиентов. Содержит в себе по одной записи для каждого взноса. Запись
содержит в себе имя потребителя, день и час оплаты, сумма оплаты, тип
сервиса, день начала сервиса и последний день сервиса.
- Таблица services, содержащяя вспомогательную информацию о типах сервисов.
- Таблица access, содержащяя по одной записи для каждой сессии
потребителя. Запись отражает в себе има потребителя, деня и час начала
сессии, день и час конца сессии.
- Таблица rejects, в которой записываются все отброшенные попытки
верификации. Содержит по одной записи для каждой попытки - день и час,
имя и пароль, переданные потребителем, причина отказа.
В целях безопасности системы пароли потребителей не следует хранить в
явном виде. Поскольку стандартная функция crypt() дает слишком слабое по
современным меркам DES криптирование, я рекомендую использовать
встроенную в SQL функцию password(). Хотя это криптирование не
использует элемент рандомизации (т.е. password() от данной
последовательности символов всегда возвращает одну и ту же
последовательность символов), оно работает быстрее crypt() (из-за
отсуствия необходимости выделять salt из криптирванного при помощи DES
пароля), к тому же этот механизм криптирования менее популярен и средств
для bruteforce атак на криптированные таким образом пароли гораздо
меньше.
СЛОЙ ВЕРИФИКАЦИИ
Слой верификации (в данном случае, написанный на Perl), выполняет
последовательность действий, которая при поступлении имени и пароля
выглядит примерно так:
1. Пытается забрать криптированный пароль для данного потребителя,
криптировать поданный потребителем пароль, взять тип сервиса, остаток
времени и - если есть - статический IP адрес (например, при помощи
"SELECT PASSWORD( 'some_pass') AS PASSWD, PASSWORD, EXPIRES, TIME_LEFT,
IP_ADDR FROM users WHERE username='some_name'").
2. Если в ответe PASSWORD пустой, то потребитель может быть сразу
отброшен, а в таблицу rejects записать сообщение о несуществующем
потребителе. Если PASSWORD и PASSWD не совпадают, то потребитель может
быть сразу отброшен, а в таблицу rejects записать сообщение об
ошибочном пароле.
3. Проверить, имеет ли потребитель право на доступ сегодня (сравнить
EXPIRES с нынешней датой). Сравнение можно облегчить, если вместо
EXPIRES в т.1 взять разницу в днях между EXPIRES и нынешним днeм,
например "TO_DAYS(EXPIRES) - TO_DAYS(CURDATE()) AS EXP". Если EXP
меньше 1, то доступ потребителю можно отказать и таблицу rejects
записать сообщение о неоплаченом сервисе.
4. Проверить сервис потребителя и если он prepaid, то нужно проверить,
является ли остаток времени TIME_LEFT положительным. Если нет, то
доступ потребителю можно отказать и таблицу rejects записать сообщение
о неоплаченом сервисе.
5. Проверить, не подключен ли уже к сети это потребитель - большенство
ISP разрешают только по одной сесии на потребителя в каждом моменте
времени - например, при помощи "SELECT COUNT(*) FROM access WHERE
username='some_user' and TIME_END IS NULL". Если число больше нуля, то
доступ потребителю можно отказать и таблицу rejects записать сообщение
о попытке повторного подключения. Исключение от правила - ISDN, если
потребителю разрешено пользоваться обоими каналами.
6. Потребителю разрешается доступ. Если у потребителя статический IP
адрес, то стоимость IP_ADDR передается RADIUS серверу при помощи пары
"Framed-IP-Address=xx.xx.xx.xx". Если такого нет, то RADIUS клиент
должен сам выбрать IP адрес для потребителя из своего пула (который
адрес появиться затем в Alive пакете). Само разрешение доступа дается
тем, что программа верификации заканчивает свое действие нулевым exit
code. Если exit code ненулевой, это и есть указание RADIUS серверу
отказать в доступе потребителю.
При получении Alive пакета слой верификации делает запись в таблице
access, в которой устанавливает имя потребителя, день и час начала
сессии, а также дополнительно желанная информация (напр., има NAS-а,
порт и др.). При этом поле в таблице, где указываются день и час
окончания сесии, остается со значением NULL, что используется для
проверки существующего подключения к сети.
При получении Stop пакета слой верификации должен найти запись,
соотвествующюю данной сессии, и дополнить ее днем и часом окончания
сессии, а также - если сервис у потребителя prepaid - вычитать из
TIME_LIMIT продолжительность сессии. При наличии одного NAS, для
опознавания сессии можно пользоваться параметром Session-ID, который
передается NAS-ом в Alive и Stop пакетах. Если воспринять этот подход,
при записи Alive пакета отмечается и Session-ID. Однако в большинстве
NAS счетчик Session-ID обнуляется при рестартировании, так что если в
сети несколько NAS одного типа, возможны ложные сигналы. В таком случае
рекомендую опознавание сесии в базе данных вести по двум параметрам,
которые тоже присуствуют в Alive и Stop пакетах - IP адрес NAS-а и порт
потребителя (NAS-IP-Address и NAS-Pord-ID). При получении Alive пакета,
IP адрес и порт отмечаются в начале сессии.
ИНТЕРФЕЙС УПРАВЛЕНИЯ
Конечной целью использования внешней верификации было иметь удобный
интерфейс для управления биллингом. При описанной структуре можно
запросто осуществлять управление потребителями, заменять пароли и т.д.
Самый интересный на мой взгляд вопрос - ввод оплаты потребителей. В
нашей системе два основных типа сервиса:
- Месячный сервис - потребитель платит фиксированную сумму и получает
доступ без всяких ограничений на 1 месяц со дня оплаты.
- Prepaid сервис - потребитель покупает некое количество часов
доступа, которыми может пользоваться в течение года.
Для эффективного управления оплатой мы ввели следующие критерии:
- Если у потребителя нет сервиса, эго новый сервис становится
активным в момент оплаты (т.е. в таблице users на сторке потребителя
должны появиться сразу же новые EXPIRES и, если надо, TIME_LIMIT
стоимости).
- Если у потребителя есть сервис, то новый сервис будет иметь
начальную дату в будущем. Для решения этого случая, каждую ночь в 00:00
выполняется небольшой скрипт, который проверяет есть ли сервисы, для
которых первый день - только-что наступивший и если да, то скрипт
делает соотвествующие изменения в таблице users. Этот механизм
позволяет также сделать перерыв в сервисе потребителя (напр., придти в
офис 5-ого июля и заплатить с 12 июля по 11 августа и затем с 28-ого
августа по 27-ое сентября).
- Если у потребителя текущий сервис - prepaid и новый тоже, то вновь
закупленные часы доступа следует прибавить к текущей стоимости
TIME_LIMIT, а к стоимости EXPIRE прибавить год.
Использование SQL позволяет также удобно вывести в уеб информацию о
предыдущих оплатах каждого клиента, делать спраки о сессиях,
расходованном и оставшемся времени (вкл. и предоставить возможность
клиенту самому наводить справки в любое время суток), показывать в
удобном виде когда и кому был отказан доступ и почему, печатать
квитанции потребителям при самой оплате и т.д.
Хммм статья интересная, но несколько устарела
в смысле использования софта ...
я бы по рекомендовал freeradius
там уже все готово :)
а cistron уже по моему умер
в смысле новых разработок
использование XtRADIUS-a с внешними приложениями даёт большие накладные расходы на вызов этих самых приложений. Мы уже через этот путь проходили, и получили кучу проблем. Далее - внешние приложения каждый раз при запуске создают соеденения с SQL сервером - это еще добавляет загрузки и что не маловажно - временной задержки. В итоге - при большом количестве работающий пользователей время авторизации может достигать больших значений, вплоть до наступления таймаута со стороны клиента.
Далее - если еще посчитать расходы вызываемые ALIVE записями (для примера - 20 пользователей на линии алайвы приходят каждые 120 сек) то система при может просто остановится.
Позволю себе совет - если не нужна MSCHAP & MASCHAP V2 авторизации то стоит использовать GNU-RADIUS или OpenRADIUS. Если нужны мелкософтовские фичи - то FreeRADIUS (хотя он и монстроватый какой-то).
>использование XtRADIUS-a с внешними приложениями даёт большие накладные расходы на вызов этих
>самых приложений. Мы уже через этот путь проходили, и получили кучу
>проблем. Далее - внешние приложения каждый раз при запуске создают соеденения
>с SQL сервером - это еще добавляет загрузки и что не
>маловажно - временной задержки. В итоге - при большом количестве работающий
>пользователей время авторизации может достигать больших значений, вплоть до наступления таймаута
>со стороны клиента.
>Далее - если еще посчитать расходы вызываемые ALIVE записями (для примера -
>20 пользователей на линии алайвы приходят каждые 120 сек) то система
>при может просто остановится.
>Позволю себе совет - если не нужна MSCHAP & MASCHAP V2 авторизации
>то стоит использовать GNU-RADIUS или OpenRADIUS. Если нужны мелкософтовские фичи -
>то FreeRADIUS (хотя он и монстроватый какой-то).
угу
иcтину глаголишь ,)
но Фри не такой уж и монтр :)
зато жир! поправил конфиги и вот тебе биллинг :)
все в MySQL(или Post или Orcale)
а пароли берет откудов угодно
начиная от простых файлов заканчивая sql или ldap
Позволю себе несколько не согласиться :)
У меня уже год как успешно работает FreeRADIUS, в биллинг (Oracle) ходит посредством внешних педалей, писаных на перле. Количество одновременных юзеров - от 500 + обработка запросов IVR. Задержка авторизации - максимум 5 сек. Правда ALIVE не юзаем - под это дело опять же педаль используется, которая наличие юзера на линии проверяет (на случай потери STOP) и денюжку периодически списывает.
Пока нет, насчет этого еще предстоит помучиться (правда насчет SIP есть некоторые наработки). Текущая IVR (AS5350 + FreeRADIUS + perl) работает как информационная служба для интернетчиков - остаток на счете узнать, платеж инет-картой перечислить...
использование XtRADIUS-a с внешними приложениями даёт большие накладные расходы на вызов этих самых приложений. Мы уже через этот путь проходили, и получили кучу проблем. Далее - внешние приложения каждый раз при запуске создают соеденения с SQL сервером - это еще добавляет загрузки и что не маловажно - временной задержки. В итоге - при большом количестве работающий пользователей время авторизации может достигать больших значений, вплоть до наступления таймаута со стороны клиента.
Далее - если еще посчитать расходы вызываемые ALIVE записями (для примера - 20 пользователей на линии алайвы приходят каждые 120 сек) то система при может просто остановится.
Позволю себе совет - если не нужна MSCHAP & MASCHAP V2 авторизации то стоит использовать GNU-RADIUS или OpenRADIUS. Если нужны мелкософтовские фичи - то FreeRADIUS (хотя он и монстроватый какой-то).
может кто-нибудь поделится готовым решением или скажет где можно его слить. Есть проблема с биллингом, т.е. нужно продавать инет в кафешке по трафику, никто не подскажет готовое решение с управлением для админа-чайника в кафешке через вебинтерфейс, буду заранее благодарен.
нормально ставится на Фре и на FC2, работает нормально до того момента пока наплыв юзверей не доходит до 20 и выше вызовов в секунду :( начинают сыпаться ерроры в лог радиуса о превышении тридов + от циски приходят периодически повторные запросы, которые радиус уже обработал, но какого-то хрена на циску это не дошло :(