BiTel

Форум BiTel
bgbilling.ru     docs.bitel.ru     wiki.bitel.ru     dbinfo.bitel.ru     bgcrm.ru     billing.bitel.ru     bitel.ru    
Текущее время: 28 апр 2024, 10:02

Часовой пояс: UTC + 5 часов [ Летнее время ]




Начать новую тему Ответить на тему  [ Сообщений: 6 ] 
Автор Сообщение
СообщениеДобавлено: 07 июн 2009, 17:35 
Не в сети

Зарегистрирован: 16 апр 2009, 00:12
Сообщения: 62
Карма: 0
Доброго дня.
Имеется скрипт на событии "Радиус-аутентификаци"

Внутри него вычисляются некие переменные, которые потом передаются NASу по телнету: errCode, TarifType, ipadr, speed.
Но телнет-сессия внутри радиус-аутентификации приводит у большому Process time
Код:
05-17/14:13:50  INFO [processor-p-2-t-29] script - Process time => 987

и может доходить до 1800, что приводит к задержке ответа сервером.
Возникла мысль передав библиотечному скрипту нужные параметры, вынести телнет-сессию, не дожидаясь её завершения, в отдельный скрипт библиотеки, используя, как описано здесь http://www.bgbilling.ru/v4.6/doc/ch02s02.html инклуд
Код:
includeBGBS( "bgbs://ru.bitel.bgbilling.kernel.script.common.bean.ScriptLibrary/default" );
Вопрос в следующем: как их правильно разнести, передав от одного другому обозначенные параметры?


Вернуться к началу
 Профиль  
 
 Заголовок сообщения:
СообщениеДобавлено: 08 июн 2009, 10:43 
Не в сети
Разработчик

Зарегистрирован: 27 ноя 2006, 20:36
Сообщения: 5715
Карма: 93
Вынесение функции в библиотеку не поможет быстрее завершить выполнение основной функции. Тут было бы уместно использовать потоки..

Код:
new Thread()
{
  public void run()
  {
      <Код для отложенного запуска>                     
  }     
}.start();


Второй вариант - писать команды в очередь в какой-нибудь файл либо БД. И выбирать эту очередь отдельной программой, выполняя команды..


Вернуться к началу
 Профиль  
 
 Заголовок сообщения:
СообщениеДобавлено: 08 июн 2009, 13:19 
Не в сети
Разработчик
Аватара пользователя

Зарегистрирован: 19 дек 2006, 21:04
Сообщения: 5970
Карма: 256
А через радиус атрибуты точно никак нельзя отправить эти параметры?

Если же нужны потоки, то лучше использовать пул. Если событие записывается в новом формате, когда интерпретируется один раз, а потом вызывается только функция, то можно использовать пул как локальную переменную. (Только при использовании локальных переменных необходимо учитывать, что новая инициализация скрипта может произойти когда угодно)
Код:
...
import java.util.concurrent.Executor;
import java.util.concurrent.Executors;

executor = Executors.newCachedThreadPool();

void onEvent( event, setup, con, conSlave ) {

   executor.execute( new Runnable()
   {
      public void run()
      {
         <Код для отложенного запуска>
      }
   } );
}


Вернуться к началу
 Профиль  
 
 Заголовок сообщения:
СообщениеДобавлено: 08 июн 2009, 14:54 
Не в сети

Зарегистрирован: 16 апр 2009, 00:12
Сообщения: 62
Карма: 0
Amir писал(а):
А через радиус атрибуты точно никак нельзя отправить эти параметры?

Однозначно нет. На насе (Микротик) создаются переменные и запускается скрипт.
Давайте я попозжа выложу этот скрипт сюда, и мы вместе подумаем, как его довести до кондиции.?!


Вернуться к началу
 Профиль  
 
 Заголовок сообщения:
СообщениеДобавлено: 08 июн 2009, 18:11 
Не в сети

Зарегистрирован: 16 апр 2009, 00:12
Сообщения: 62
Карма: 0
Собственно скрипт
Код:
import bitel.billing.server.tariff.bean.*;
import bitel.billing.server.radius.*;
import bitel.billing.server.contract.bean.*;
import bitel.billing.server.script.bean.event.*;
import bitel.billing.server.util.*;
import java.mysql.*;
import bitel.billing.common.*;
import bitel.billing.server.util.telnet.TelnetSession;
import java.util.*;

speed = 0;
TarifType = 0;
cid = 0;
DateNow = new GregorianCalendar();
errCode = event.getErrorCode();
request = event.getRequest();
maclogin = request.getStringAttribute(RadiusStandartAttributes.Calling_Station_Id);
User_Name = request.getStringAttribute(RadiusStandartAttributes.User_Name);
login = event.getLogin();
loginid = login.getId();
ps = con.prepareStatement( "SELECT ip, mac_adr, mac_date FROM radius_pair_ip_1 WHERE id=?");
ps.setInt( 1, loginid );
rs = ps.executeQuery();
login_ip = 0;
if( rs.first() )
{
 login_ip = rs.getLong( 1 );
 ipadr = IPUtils.convertIpToString( login_ip );
 macbase = rs.getString( 2 );
 last_mac_change = rs.getDate ( 3 );
}
if( ((errCode != 0) && (errCode != 2)) || (errCode == 33))
{
 ps = con.prepareStatement( "UPDATE user_login_1 SET connected=0 WHERE id=?" );
 ps.setInt( 1, loginid );
 ps.executeUpdate();
 // разрешим логин с виртуальной сессией для перенаправления на странички ошибок
 // кого и куда направить, знает микротик по errcode
 response = event.getResponse();
 response.setPacketType( RadiusPacket.AUTHENTICATION_ACCEPT );
 // Готовим аттрибуты на отдачу
 // Service-Type = 2
 raSt = new RadiusAttribute( 6 );
 raSt.setIntValue( 2 );
 // Framed-Protocol = 1
 raFp = new RadiusAttribute( 7 );
 raFp.setIntValue( 1 );
 // Framed-IP-Adress
 raIp = new RadiusAttribute( 8 );
 raIp.setIntValue((int) login_ip );
 //Session-Timeout = 900 (15 min )
 raStm = new RadiusAttribute( 27 );
 raStm.setIntValue( 900 );
 // Framed-Pool = suspensed
 /*raFl = new RadiusAttribute( 88 );
 raFl.setStringValue( "suspensed" );*/
 response.addAttribute( raSt );
 response.addAttribute( raFp );
 response.addAttribute( raIp );
 response.addAttribute( raStm );
 //response.addAttribute( raFl );
}
if (macbase == null || last_mac_change == null)
{
 DateNowSql = TimeUtils.convertCalendarToSqlDate ( DateNow );
 psup = con.prepareStatement( "UPDATE radius_pair_ip_1 SET mac_adr=?, mac_date=? WHERE id=?" );
 psup.setString ( 1, maclogin );
 psup.setDate( 2, DateNowSql );
 psup.setInt ( 3, loginid );
 psup.executeUpdate();
 macbase = maclogin;
}
if (last_mac_change != null && !maclogin.equals(macbase))
{
 delta = TimeUtils.daysDelta (TimeUtils.convertSqlDateToCalendar ( last_mac_change ), DateNow );   
 if (!maclogin.equals(macbase) &&  delta  > 30 )
 {
  DateNowSql = TimeUtils.convertCalendarToSqlDate ( DateNow );
  psup = con.prepareStatement( "UPDATE radius_pair_ip_1 SET mac_adr=?, mac_date=? WHERE id=?");
  psup.setString ( 1, maclogin );
  psup.setDate( 2, DateNowSql );
  psup.setInt ( 3, loginid );
  psup.executeUpdate();
  macbase = maclogin;
 }
}
if (!maclogin.equals(macbase) )
{
  errCode = 27;
  print ( "AUTHENTICATION_REJECT but mac's non equals");
  print ("login_ip: " + ipadr);
  print ("mac from radius: " + maclogin);
  print ("mac from base: " + macbase);
}
if ( errCode == 0 )
{
 ps = con.prepareStatement( "UPDATE user_login_1 SET connected=1 WHERE id=?" );
 ps.setInt( 1, loginid );
 ps.executeUpdate();
 // из текущего тарифа получаем нужную полосу
 cid = event.getContractID();
 ctm =  new ContractTariffManager( con );
 currentTariff = ctm.getContractTariff( cid, DateNow ).getTariffPlanID();
 switch ( currentTariff )
 {
  case 2:
  TarifType = 2;
  break;
  case 7:
  speed = 256000;
  TarifType = 3;
  break;
  case 8:
  speed = 512000;
  TarifType = 3;
  break;
  case 10:
  speed = 768000;
  TarifType = 3;
  break;
  case 11:
  speed = 1024000;
  TarifType = 3;
  break;
  case 12:
  TarifType = 1;
  break;
 }
}
if( ((errCode == 0) || (errCode == 4)) || (errCode == 27) || (errCode == 33))
// Ошибки  0 - все ОК, 4 - нет денег,   27 - неверный МАК,   33 - договор приостановлен
{
//includeBGBS( "bgbs://ru.bitel.bgbilling.kernel.script.common.bean.ScriptLibrary/Telnet_Logon" );

//цепляемся к микротику
 host = ( "192.168.8.1" );
 port = (23);
 login = ( "login+ct" );
 pswd = ("password");
 session = null;   
 try
  {
   session = new TelnetSession( host, port );
   session.setLoginPromptSequence( ":" );
   session.connect();
   session.doCommand( login );
   session.setLoginPromptSequence( ">" );
   session.doCommand( pswd );
   session.doCommand ( ":global ErrCode " + errCode);
   session.doCommand ( ":global TarifType " + TarifType);
   session.doCommand ( ":global UserIp " + ipadr);
   session.doCommand ( ":global ContractId " + cid);
   session.doCommand ( ":global UserName " + User_Name);
   session.doCommand ( ":global UserSpeed " + speed);
   session.doCommand ("/system script run [/system script find name=Logon_Script]");
   session.doCommandAsync( "quit" );
  }
 catch( Exception e )
 {
  throw new RuntimeException( e );
  print ( "connect error " );
  }
 finally
 {
  if ( session != null )
   {
    session.disconnect();
   }      
  }   
}


Только я чет как-то не нашёл, как использовать новый формат для этого события.
Кому интересен функционал этого скрипта, не копируйте без разбора, т.к. в нем используются самостоятельно добавленные столбцы и самописные скрипты в микротике. Описалово выложим в вики после доводки до ума.


Вернуться к началу
 Профиль  
 
 Заголовок сообщения:
СообщениеДобавлено: 12 июн 2009, 00:23 
Не в сети

Зарегистрирован: 16 апр 2009, 00:12
Сообщения: 62
Карма: 0
Благодарю, расковырял.
получилось
Код:
6-11/21:43:34  INFO [pool-1-thread-5] EventProcessor - Process event cid:2; event:Event bitel.billing.server.processor.event.RadiusAuthenticationEvent cid: 2; module: 1; type: 120
06-11/21:43:34  INFO [pool-1-thread-5] ScriptInstance - Invoke method Function [id:2; title:Login_script] : onEvent
06-11/21:43:34  INFO [pool-1-thread-5] script - Process time => 21


Вернуться к началу
 Профиль  
 
Показать сообщения за:  Поле сортировки  
Начать новую тему Ответить на тему  [ Сообщений: 6 ] 

Часовой пояс: UTC + 5 часов [ Летнее время ]


Кто сейчас на конференции

Сейчас этот форум просматривают: нет зарегистрированных пользователей и гости: 1


Вы не можете начинать темы
Вы не можете отвечать на сообщения
Вы не можете редактировать свои сообщения
Вы не можете удалять свои сообщения
Вы не можете добавлять вложения

Найти:
Перейти:  
POWERED_BY
Русская поддержка phpBB
[ Time : 0.204s | 30 Queries | GZIP : On ]