{~Create195_IK_BDPD_2965
  exchange #2965
  создание эд 195го по блоку IK.BD
  aBDPD - раздел IK.BDPD по которому определено создание эд 195го по ФТ-1.

  }
function Create195_IK_BDPD_2965( aBudgetID: string;
                                 aED, aIK, aBDPD: Variant;
                                 aCfg_CreateParamAUBU: string;
                                 aEDInfo: string): boolean;
var
  xXML: Variant;
  xDocInfo: string;
  xID: string;
  xDoc193ID: string;
  xBDPD_NOM_PP: string;
  xBDPD_DATE_PP: string;
  xBDPD_SUM_PP: string;
  xBDPD_GUID: string;
  xXmlDoc195: Variant;
  xDoc195: Variant;
  xPAY_ID: string;
  i,i2: integer;
  xBDPDST: Variant;
  xDoc195Lines: Variant;
  xDoc195Line: Variant;
  xIndustryCodes: TStringList;
  xBDPD_KBK: string;
  xREC_ACCOUNT: string;
  xProblems: boolean;
  xPAY_ACCOUNT: string;
  xAmount: currency;
  xOrgID: string;

  {~SetParamDoc195FromED_
    копирование поля из ED (aParamED) в Doc195 (aParamDoc195).
    отсутствующее поле в ED будет заменено пустой строкой.}
  procedure SetParamDoc195FromED_( aParamDoc195, aParamED: string);
  begin

      try
        xDoc195.SetAttribute( aParamDoc195, GetNodeAttributeEx( aED, aParamED));

        except
          ExceptionLog( 'Сбой SetParamDoc195FromED_');
      end;

  end;


  {~DoSearchOtrKod_
    поиск отр.кода в справочнике "правила соответствия классификаторов бу/ау"
    по л/с (маска) и квфо. тип субсидии = "не указан" (=3).
    проблема в том, что в справ. соответствий отр код указывается как маска.
    поэтому, если нашелся отр код в правилах, его нужно проверить: это маска
    или значение ?
      если маска - поискать в справочнике,
      если значение - тоже искать на наличие его в справочнике.
    причем отр.код нужно проверять с привязкой к бюджету создаваемого эд
    195го класса.
    если код не будет найден в правилах, нужно вернуть нулевой код
    с учетом маски.}
  function DoSearch_INDUSTRYCODE_( aFSR: string): string;
  var
    xXml: Variant;
    xRootXml: Variant;
    xNodeXml: Variant;
    i,j: integer;
    xFoundCount: integer;
    xIndustryCode: string;
    xIndustryCodeID: string;
    xFoundIndustryCodeID: string;
    xLSMaska: string;
    xIndustryMaska: string;
    xFound: boolean;
  begin

      try
        Result := '';

        // системный отр.код - по умолчанию
        // если код не будет найден - возвращается пустое значение
        xXml :=  QueryXml( ' select g.id from INDUSTRYCODE g'
                          +' where g.budget_id=? and g.code=?',
                           [ aBudgetID,
                             FormatKbk( 'INDUSTRYCODE', '0', aBudgetID)]);
        try
          xRootXml := xXml.documentElement;
          if (xRootXml.childNodes.Length <> 1) then begin
            WriteInfo( FORMAT( 'Не найден нулевой отраслевой код для бюджета %s.',
                               [ aBudgetID]));
            EXIT;
          end;
          Result := xRootXml.childNodes.Item[0].GetAttribute('ID');
          finally
            xXml.LoadXml( '');
        end;


        xIndustryCodes.Clear;    // еще ничего не нашли

        // здесь "тип субсидии" привязываем к Id=3, а не ищем строку "Не указан"
        // в справочнике "типы субсидий"
        // exchange #2872
        // добавлена привязка к бюджету
        xXml :=  QueryXml( ' Select Accountnumber_Mask, Industrycode_Mask'
                          +' From AubuclassifiersRules'
                          +' where GrantinvestmentType = 3 and Fsr_Id=?'
                          +' and budget_id=?',
                            [ aFSR,
                              aBudgetID]);
        try
          xRootXml := xXml.documentElement;
          // здесь ищем все маски отр кодов в соответствии с л/с.
          // причем игнорируем одинаковые маски отр.кодов
          for i := 0 to xRootXml.childNodes.Length - 1 do begin
            xNodeXml      := xRootXml.childNodes.Item[i];
            xLSMaska      := VarToStr( xNodeXml.getAttribute('ACCOUNTNUMBER_MASK'));
            xIndustryMaska:= VarToStr( xNodeXml.getAttribute('INDUSTRYCODE_MASK'));
            // проверяем маску на идентичность счета
            if (xLSMaska = xPAY_ACCOUNT) then begin

              if (xIndustryCodes.IndexOf( xIndustryMaska) = -1)
                then xIndustryCodes.Add( xIndustryMaska);
            end else
              // проверяем л/с на совпадение по маске
              if MatchesMask( xPAY_ACCOUNT, xLSMaska) then begin

                if (xIndustryCodes.IndexOf( xIndustryMaska) = -1)
                  then xIndustryCodes.Add( xIndustryMaska);
              end;
          end;//for//
          finally
            xXml.LoadXml( '');
        end;


        // теперь пробуем понять, что из найденных масок есть в справочнике
        // отр. кодов
        if (xIndustryCodes.Count > 0) then begin
          // пока считаем что ничего не нашли
          xFoundCount          := 0;
          xFoundIndustryCodeID := '';
          // получаем список отр.кодов для бюджета из справочника
          xXml :=  QueryXml( ' select g.id, g.code from INDUSTRYCODE g'
                            +' where g.budget_id=?',
                             [ aBudgetID]);
          try
            // пробуем найти отр.код, соответствующий найденным маскам
            // из правил
            xRootXml := xXml.documentElement;
            for i := 0 to xIndustryCodes.Count - 1 do begin
              xIndustryMaska := xIndustryCodes.Strings[i];
              for j := 0 to xRootXml.childNodes.Length - 1 do begin
                xNodeXml        := xRootXml.childNodes.Item[j];
                xIndustryCodeID := VarToStr( xNodeXml.GetAttribute('ID'));
                xIndustryCode   := VarToStr( xNodeXml.GetAttribute('CODE'));

                // проверяем маску на идентичность отр.кода
                if (xIndustryMaska = xIndustryCode) then begin
                  xFound := TRUE;

                end else
                  // проверяем отр.код на совпадение по маске
                  if MatchesMask( xIndustryCode, xIndustryMaska) then begin
                    xFound := TRUE;

                  end else
                    xFound := FALSE;

                // здесь проверяем, если это один и тот же отр код,
                // тогда его за найденный не считаем.
                // такое может быть, если есть разные маски, которые
                // удовлетворяют одному и тому же отрг.коду.
                if xFound then
                  if (xFoundIndustryCodeID <> xIndustryCodeID) then begin
                    INC( xFoundCount);
                    if (xFoundCount > 1) then begin

                      // найдено несколько отр кодов - заполняем отр. код нулевым
                      EXIT;
                    end;
                    xFoundIndustryCodeID := xIndustryCodeID;
                  end;
              end;//for//
            end;//for//
            finally
              xXml.LoadXml( '');
          end;
          // если найден единственный код - возвращаем его как результат.
          // проверка нужна на случай если не найдено ни одного отр.кода.
          if (xFoundCount = 1)
            then Result := xFoundIndustryCodeID;
        end;
        except
          ExceptionLog( 'Сбой DoSearch_INDUSTRYCODE_');
      end;

  end;
  {----------------------------------------------------------------------------}
  {~SetLineDoc195FromED_}
  procedure SetLineDoc195FromED_( aLine195, {aLineED}aBDPDST: Variant;
                                  aDocID: string);
  var
    xBDPDST_KBK: string;
    xResFound: string;
  begin

      try
        // сумма
        aLine195.SetAttribute( 'AMOUNT',
                               GetNodeAttributeEx( aBDPDST, 'SUM'));


        // exchange #3081 - строка
        // загрузка косгу/квр + новые поля для классификации получателя
        if NOT FillAndCheck_LineED_AuBu_by3081(
                                aBudgetID,
                                aLine195,
                                GetNodeAttributeEx( aBDPDST, 'KBK'),
                                GetNodeAttributeEx( aBDPDST, 'TYPE_KBK'),
                                '195',
                                0,
                                GetNodeAttributeEx( aED, 'PAY_ID'))
          then xProblems := TRUE;

        {   Если значение «999» существует в справочнике «Классификатор операций
          сектора государственного управления», то заполнять «999» (считается
          найденным в справочнике для ФТ-2.5).
            Иначе заполнять поле значением с 18 по 20 знак BDPDST.KBK,
          если BDPDST.KBK пустое, то заполнять (либо не заполнять)
          в зависимости от значения параметра «Заменять значение
          аналитического кода АУ/БУ в строке на 0 при отсутствии
          в справочнике» (ФТ-2.5).
          exchange #3081
          это оставлено, но заполняется уже после заполнения полей
          по exchange #3081, поскольку тогда будет заполнено или косгу или квр,
          а заполнение косгу =999 будет позже.}
        if KbkExists( aBudgetID, '999', 'Kes')
          then aLine195.SetAttribute( 'KESR_CODE', '999');
          (*
          else begin
            xBDPDST_KBK := GetNodeAttributeEx( aBDPDST, 'KBK');
            // берем 3 последних символа BDPDST.KBK, если поле >=3 символов
            if (LENGTH( xBDPDST_KBK) >= 3) then
              if NOT FillKES_for_Line_Created_ED(
                              aBudgetID,
                              xDoc195,
                              'KESR_CODE',
                              COPY( xBDPDST_KBK, LENGTH( xBDPDST_KBK) - 2, 3),
                              aCfg_CreateParamAUBU,
                              'КОСГУ (из BDPDST.KBK) %s не найден в БД')
                then xProblems := TRUE;
          end;
*)

        // КВФО=8
        aLine195.SetAttribute( 'FSR_ID', '8');

        // назначение платежа - не заполнять
        aLine195.SetAttribute( 'DESCRIPTION', '');

        // примечание - не заполняется
        aLine195.SetAttribute( 'NOTE', '');

        // обязательство - не заполняется
        //aLine195.SetAttribute( 'ORG_ID', '');

        // отр.код - всегда после квфо!
        aLine195.SetAttribute( 'INDUSTRYCODE_ID',
                               DoSearch_INDUSTRYCODE_(
                                      GetNodeAttributeEx( aLine195, 'FSR_ID')));

        // код субсидии
        // Заполнять значением BDPDST.ADD_KLASS, если значение данного
        // реквизита пустое, то заполнять системными нулями.
        // exchange #2987 - дополнительное сообщение
        // exchange #3014 - поиск с учетом учредителя
        aLine195.SetAttribute(
                'GRANTINVESTMENT_ID',
                SearchGrandinvestmentCodeEx(
                                  aBudgetID,
                                  GetNodeAttributeEx( aBDPDST, 'ADD_KLASS'),
                                  xResFound,
                                  TRUE,
                                  aDocID));
        if (LENGTH( xResFound) > 0) then
          if (xResFound <> '1')
            then xProblems := TRUE;

        except
          ExceptionLog( 'Сбой SetLineDoc195FromED_');
      end;

  end;


begin

    try
      Result := TRUE;    // считаем что создание 195го выполнено

      xBDPD_NOM_PP  := GetNodeAttributeEx( aBDPD, 'NUM_PP');
      xBDPD_DATE_PP := GetNodeAttributeEx( aBDPD, 'DATE_PP');
      xBDPD_SUM_PP  := GetNodeAttributeEx( aBDPD, 'SUM_PP');
      xBDPD_GUID    := GetNodeAttributeEx( aBDPD, 'GUID_FK');

      xDocInfo := aEDInfo;
      {
      FORMAT( '"%s" № %s Дата: %s Сумма: %s',
                           [ 'Заявка БУ/АУ на выплату средств',
                             xBDPD_NOM_PP,
                             xBDPD_DATE_PP,
                             xBDPD_SUM_PP]);
                             }

      // пересчитываем сумму по строкам, а затем сверяем итоговую сумму
      // с суммой из поля BDPD.SUM_PP. в логе указываем расхождение,
      // но поиск эд будем делать, все таки, по сумме из BDPD.SUM_PP.

      xAmount := 0.0;
      for i := 0 to aBDPD.childNodes.Length - 1 do
        if (aBDPD.childNodes.Item[i].NodeName = 'BDPDST') then begin
          xBDPDST := aBDPD.childNodes.Item[i];
          xAmount := xAmount
                      + StrToCurrDef( GetNodeAttributeEx( xBDPDST, 'SUM'), 0);
        end;

      if ( FORMAT( '%.2f', [ StrToCurrDef( xBDPD_SUM_PP, 0)])
           <> FORMAT( '%.2f', [ xAmount]))
        then WriteInfo( FORMAT( 'Обнаружено расхождение сумм по блоками BDPDST (поля SUM) %s '
                               +'со значением в поле BDPD.SUM_PP %s.',
                                [ FORMAT( '%.2f', [ xAmount]),
                                  xBDPD_SUM_PP]));

      //------------------------------------------------------------------
      { Проверить наличие в системе ЭД класса 195 с номером, датой, суммой
        и реквизитами плательщика, соответствующими NOM_PP, DATE_PP,SUM_PP и
        (INN_PAY и KPP_PAY ) блока BDPD}
      xXML := QueryXml(  ' Select A.ID ID, A.FOREIGN_KEY FK, A.dispstatus_id DS'
                        +' From Document D'
                        +' Left Join aubucashrequest A on A.Document_Id = D.Id'
                        +' Where D.Budget_Id = ? and D.DocumentClass_Id = 195'
                        +' and LTrim(A.Doc_Number) = ? and A.Doc_Date = ?'
                        +' and a.amount = ?'
                        +' and (A.title_id=A.id or A.title_id is null)'
                        +' and A.dispstatus_id>-1'
                        +' and A.PAY_TAXCODE=? and A.PAY_KPP=?',
                        [ aBudgetID,
                          xBDPD_NOM_PP,
                          // дата описана в хмл как dd.mm.yyyy
                          StrToDate( xBDPD_DATE_PP),
                          // есть проблема с передачей значения как число
                          // поэтому передаем строкой из BDPD.SUM_PP
                          xBDPD_SUM_PP,
                          // реквизиты плательщика
                          GetNodeAttributeEx( aBDPD, 'INN_PAY'),
                          GetNodeAttributeEx( aBDPD, 'KPP_PAY')],
                        // без кеша
                        FALSE);

      xXML := xXml.documentElement;
      case xXML.childNodes.Length of
         0: begin { заглушка } end;

         1: begin
              xXML := xXml.childNodes.Item[ 0];
              xID  := GetNodeAttributeEx( xXML, 'ID');
              // если значение пустое и статус «Готов к исполнению»,
              if ((LENGTH( GetNodeAttributeEx( xXML, 'FK')) <= 0)
                  AND (GetNodeAttributeEx( xXML, 'DS') = '86')) then begin
                WriteLog( 'ЭД найден в БД с незаполненным FOREIGN_KEY на 86м статусе - будет обновлен.');
                // то присваиваем полю значение GUID_FK
                UpdateDocumentForegnKey( '195', xID, xBDPD_GUID);
                // вызываем метод
                // формирования ЭД класса 193, доводим его до статуса
                // «Обработка завершена», переходим к следующему ЭД
                // в загружаемом файле.
                if CreateAndLinkDoc193_spawn_moneytransfer( aBudgetID,
                                                            xID,
                                                            '195',
                                                            xBDPD_NOM_PP,
                                                            xBDPD_DATE_PP,
                                                            xBDPD_SUM_PP)
                  then begin
                    // доводим эд 193й до 10го статуса
                    xDoc193ID := QueryField(  ' select m.id ID from moneytransferorder m'
                                             +' join document d on d.id=m.document_id'
                                             +' join aubucashrequest p on p.document_id=d.parent_id'
                                             +' where p.ID = ? and d.documentclass_id=193'
                                             +' and (m.title_id=m.id or m.title_id is null)'
                                             +' and (m.dispstatus_id>-1)',
                                              [ xID],
                                              'ID');
                    EDMoveToStatus( aBudgetID,
                                    xDoc193ID,
                                    '193',
                                    '10',
                                    '1=finalize');
                  end;
              end else begin
                WriteLog( 'ЭД найден в БД с заполненным FOREIGN_KEY или не на 86м статусе - не обновляется.');
              end;
              EXIT;
            end;

      else begin
            // работаем по старому
            Result := FALSE;
            EXIT;
          end;
      end;//case//

      // в логе указываем что эд 5/24 не создается.
//      WriteLog( aEDInfo + ' - не создается.', True);
      // формируется 195й
//      WriteLog( 'Формируется ' + xDocInfo, True);

      //------------------------------------------------------------------
      // создаем ЭД 195го класса
      xProblems := FALSE;

      xXmlDoc195 := CreateOleObject('Microsoft.XmlDom');
      xDoc195 := xXmlDoc195.appendChild(
                                     xXmlDoc195.createElement('DOCUMENT'));
      xDoc195.SetAttribute( 'action', 'insert');
      xDoc195.setAttribute( 'class', '195');
      xDoc195.setAttribute( 'BUDGET_ID', aBudgetID);
      // это поле необходимо для линковки - заполняется при создании ЭД 5го класса
      SetParamDoc195FromED_( 'GUID', 'GUID');
      // признак загрузки из файла IK
      xDoc195.SetAttribute( 'F_ORIGINAL_TYPE', 'IK');
      // бюджет
      xDoc195.SetAttribute( 'F_BUDGET_ID', aBudgetID);
      // из BDPD.GUID_FK
      xDoc195.SetAttribute( 'FOREIGN_KEY', xBDPD_GUID);
      //SetParamDoc195FromED_( 'GUID', 'GUID');
      // Дата документа
      // строка должна быть в формате YYYY-MM-DD
      xDoc195.SetAttribute( 'DOC_DATE',
                            DateTimeToXml( StrToDate( xBDPD_DATE_PP)));
      // Номер документа
      xDoc195.SetAttribute( 'DOC_NUMBER', xBDPD_NOM_PP);

      // Тип операции
      // присваивать значение поля «Имя» справочника
      // «Типы операций с документами» равное «Внебанковская операция» (-29).
      // Если такое значение в справочнике отсутствует, то выдавать сообщение
      // в журнал о незаполнении поля, поле не заполнять.
      // По-умолчанию заполняется значением, выбранным для 195 класса
      // в справочнике «Типы операций по-умолчанию», а в случае отсутствия
      // настройки, значением «Не указано»
      if (QueryField( 'select count( * ) N from opertype where id=?',
                      [ '-29'],
                      'N') <> '1')
        then WriteInfo( 'Поле "Тип операции" не заполняется - в БД не '
                       +'найдено значение «Внебанковская операция» (-29).')
        else xDoc195.SetAttribute( 'OPERTYPE_ID', '-29');
            {
      xDoc195.SetAttribute( 'OPERTYPE_ID',
                            OperTypeDefaultForClassEx( '195'));
                            }

      // Сумма	Сумма выписки
      // Сумма по всем строкам документа - ?
      xDoc195.SetAttribute( 'AMOUNT', xBDPD_SUM_PP);
      // вид платежа
      SetParamDoc195FromED_( 'PAYKIND', 'PAYKIND');

      // вид операции
      SetParamDoc195FromED_( 'BANKOPER_ID', 'BANKOPER_ID');
      // если поле вида операции не заполнено, заполняем значением =1
      // (платежное поручение)
      if (LENGTH( VarToStr( xDoc195.GetAttribute( 'BANKOPER_ID'))) <= 0)
        then xDoc195.SetAttribute( 'BANKOPER_ID', '1');

      // очередность
      SetParamDoc195FromED_( 'QUEUE_KIND', 'QUEUE_KIND');
      // Дата исполнения	- Дата по банку
      SetParamDoc195FromED_( 'CARRY_DATE', 'CARRY_DATE');
      // Дата регистрации - не заполянется
      //SetParamDoc195FromED_( 'REG_DATE', '');
      // Дата подтверждения остатка - не заполянется
      //SetParamDoc195FromED_( 'CONFIRM_DATE', '');
      // Дата списания со счета - Дата по банку
      SetParamDoc195FromED_( 'DEBIT_DATE', 'CARRY_DATE');
      // Код ФАИП
      SetParamDoc195FromED_( 'PL_FAIP_OBJ_ID', 'PL_FAIP_OBJ_ID');
      SetParamDoc195FromED_( 'PL_FAIP_OBJ_CODE', 'PL_FAIP_OBJ_CODE');
      // От ФК. Признак всегда включен.
      xDoc195.SetAttribute( 'FK_FLAG', '1');
      // Предельная дата исполнения	- Дата по банку
      SetParamDoc195FromED_( 'LIMITING_DATE', 'CARRY_DATE');
      // Обязательство - Не заполняется
      //SetParamDoc195FromED_( 'ACCEPTED_OBL_ID', '');
      // Возврат б/права расходования -	Не заполняется
      //SetParamDoc195FromED_( 'WO_SPENDING', '0');
      // Авансовый платеж			Не заполняется
      //SetParamDoc195FromED_( 'ADVANCE_PAYMENT', '0');
      // Вид операции по ЛС			Не заполняется
      //SetParamDoc195FromED_( 'OPERKIND_ID', '');
      // НДС		Нет	значение по умолчанию «0.00»
      xDoc195.SetAttribute( 'VAT', '0.00');
      // Внешний статус	- «Не выгружен» (не выгружается)
      //xDoc195.SetAttribute( 'EXTSTATUS_ID', '0');
      // Вид документа в ФК	- Заполняется значением «Платежное поручение»
      xDoc195.SetAttribute( 'PAYDOC_CODE', 'PP');
      // Результат проверки			Не заполняется
      xDoc195.SetAttribute( 'CHECK_RESULT', '');
      // Комментарий			Не заполняется
      xDoc195.SetAttribute( 'REMARK', '');
      // Назначение платежа -	из Основания в ЭД 5го класса
      SetParamDoc195FromED_( 'DESCRIPTION', 'DESCRIPTION');

      // Учредитель - Автозаполнение из справочника «Организации»
      // по механизму поиска в ЭД - по полю «Код вышестоящего ГРБС»
      // организации – плательщика.
      xPAY_ID       := GetNodeAttributeEx( aED, 'PAY_ID');
      xPAY_ACCOUNT  := GetNodeAttributeEx( aED, 'PAY_ACCOUNT');
      if (LENGTH( xPAY_ID) > 0) then begin
        xDoc195.SetAttribute(
                    'ORG_ID',
                    QueryField( 'Select o.MANAGER_ID from org o where o.id=?',
                                [ xPAY_ID],
                                'MANAGER_ID'));
        // название учредителя - оф.название орг.
        xDoc195.SetAttribute(
                    'ORG_NAME',
                    QueryField( 'Select o.DESCRIPTION from org o where o.id=?',
                                [ xDoc195.GetAttribute( 'ORG_ID')],
                                'DESCRIPTION'));
      end;

      // Блок «Плательщик»
      // Одноименные реквизиты блока «Плательщик» ЭД класса 5
      SetParamDoc195FromED_( 'PAY_ID', 'PAY_ID');
      // ИНН
      SetParamDoc195FromED_( 'PAY_TAXCODE', 'PAY_TAXCODE');
      // КПП
      SetParamDoc195FromED_( 'PAY_KPP', 'PAY_KPP');
      // Организация
      SetParamDoc195FromED_( 'PAY_NAME', 'PAY_NAME');
      // Счет
      SetParamDoc195FromED_( 'PAY_ACC_ID', 'PAY_ACC_ID');
      SetParamDoc195FromED_( 'PAY_ACCOUNT', 'PAY_ACCOUNT');
      // БИК
      SetParamDoc195FromED_( 'PAY_BIC', 'PAY_BIC');
      // Банк
      SetParamDoc195FromED_( 'PAY_B_NAME', 'PAY_B_NAME');
      // Корсчет
      SetParamDoc195FromED_( 'PAY_CORACCOUNT', 'PAY_CORACCOUNT');
      // УФК
      SetParamDoc195FromED_( 'PAY_UFK_NAME', 'PAY_UFK_NAME');
      // Счет УФК
      SetParamDoc195FromED_( 'PAY_UFK_ACC_ID', 'PAY_UFK_ACC_ID');
      SetParamDoc195FromED_( 'PAY_UFK_ACCOUNT', 'PAY_UFK_ACCOUNT');
      SetParamDoc195FromED_( 'PAY_FILIAL_NAME', 'PAY_FILIAL_NAME');
      SetParamDoc195FromED_( 'PAY_FILIAL_CODE', 'PAY_FILIAL_CODE');

      // скрытые поля из ЭД 5го класса
      // Код клиента (CLIENT_CODE)	PAY_CODE		Скрытые поля
      SetParamDoc195FromED_( 'CLIENT_CODE', 'PAY_CODE');
      // Код ФК (FK_CODE)	PAY_OFK_CODE
      SetParamDoc195FromED_( 'FK_CODE', 'FK_CODE');

      // блок «Получатель»
      // Значением одноименных полей блока «Получатель» ЭД класса 5.
      SetParamDoc195FromED_( 'REC_ID', 'REC_ID');
      // ИНН
      SetParamDoc195FromED_( 'REC_TAXCODE', 'REC_TAXCODE');
      // КПП
      SetParamDoc195FromED_( 'REC_KPP', 'REC_KPP');
      // Организация
      SetParamDoc195FromED_( 'REC_NAME', 'REC_NAME');
      // Счет
      SetParamDoc195FromED_( 'REC_ACC_ID', 'REC_ACC_ID');
      SetParamDoc195FromED_( 'REC_ACCOUNT', 'REC_ACCOUNT');
      // БИК
      SetParamDoc195FromED_( 'REC_BIC', 'REC_BIC');
      // Банк
      SetParamDoc195FromED_( 'REC_B_NAME', 'REC_B_NAME');
      SetParamDoc195FromED_( 'REC_CORACCOUNT', 'REC_CORACCOUNT');

      // exchange #2891
      // если поле REC_CORACCOUNT пустое, то при вставке 5го с пустым полем
      // в АЦК-Ф поле заполнится по карточке банка по REC_BIC,
      // а в 195м такого алгоритма нет. поэтому тут реализуем такой же
      // механизм: ищем описание банка по БИК и заполняем кор счет оттуда

      if (LENGTH( xDoc195.GetAttribute( 'REC_CORACCOUNT')) <= 0)
        then xDoc195.SetAttribute(
                      'REC_CORACCOUNT',
                      QueryField( 'select CORACCOUNT C from bank where bic=?',
                                  [ xDoc195.GetAttribute( 'REC_BIC')],
                                  'C'));

      // УФК
      SetParamDoc195FromED_( 'REC_UFK_NAME', 'REC_UFK_NAME');
      // Счет УФК
      SetParamDoc195FromED_( 'REC_UFK_ACC_ID', 'REC_UFK_ACC_ID');
      SetParamDoc195FromED_( 'REC_UFK_ACCOUNT', 'REC_UFK_ACCOUNT');
      // Доп. офис
      SetParamDoc195FromED_( 'REC_FILIAL_NAME', 'REC_FILIAL_NAME');
      SetParamDoc195FromED_( 'REC_FILIAL_CODE', 'REC_FILIAL_CODE');

      // закладка ГТС ГМП - УИН
      SetParamDoc195FromED_( 'CHARGE_NUMBER', 'UIN');

      // Реквизиты возвращаемого документа - Не заполняется

      // Закладка «Ответственные лица»
      if (LENGTH( xPAY_ID) > 0) then begin
        // Ответственные лица определяются по организации плательщику
        // руководитель: код=-2
        UpdateRespersonM1ByOrgID_IntoXML(
              xDoc195,
              'CHIEF_',
              xPay_ID,
              ' and Rp.appointment_id = -2 and Rp.Actual_flag=1',
              aBudgetID,
              '195',
              '-2');
        // гл.бух: код=-3
        UpdateRespersonM1ByOrgID_IntoXML(
              xDoc195,
              'BUH_',
              xPay_ID,
              ' and Rp.appointment_id = -3 and Rp.Actual_flag=1',
              aBudgetID,
              '195',
              '-3');
      end;
      // Дата подписания - Заполняется датой документа.
      // ожидается формат YYYY-MM-DD
      xDoc195.SetAttribute( 'SIGN_DATE', xDoc195.GetAttribute( 'DOC_DATE'));

      //------------------------------------------------------------------
      // Поле «Идентификатор платежа» формируется из ЭД класса 5
      CopyDepartmentalInfo( xDoc195, aED);
      // exchange #3081
      // Если, BD.KBK имеет непустое значение, то сохранять значение
      // в поле «Идентификатор платежа» с типом «Доходы».
      xBDPD_KBK := GetNodeAttributeEx( aBDPD, 'KBK');
      if (LENGTH( xBDPD_KBK) > 0) then begin

        xDoc195.SetAttribute( 'PI_ANAL_KIND', '1');
        xDoc195.SetAttribute( 'PI_BUDGET_CODE', xBDPD_KBK);
      end;

      //------------------------------------------------------------------
      // этот список нужен при поиске отр.кодов для строк
      xIndustryCodes:= TStringList.Create;
      try
        // поля «Счет» блока получателя
        xREC_ACCOUNT := GetNodeAttributeEx( xDoc195, 'REC_ACCOUNT');

        { ФТ-2.2	Поля блока «Классификация получателя» ЭД класса 195
          заполнить значениями из соответствующих полей структурированного файла}

        // КОСГУ	Если значение первых двух символов поля «Счет» блока получателя
        // равно «30», то  значению поля присвоить «888»;
        // Иначе заполнять поле значением с 18 по 20 знак BDPD.KBK,
        // если BDPD.KBK пустое, то поле не заполнять.
        // при этом сразу проверяем код в бд с заменой на 0.
        // если код не найден в бд - это считается проблемой описания эд
        // здесь при проверке кода в бд, отсутствие кода не является проблемным
        // для эд 195го. проблемы будут у создаваемого 193го.
        // поэтому если в бд код не найден, поле заполняем пустым значением.
        if (POS( '30', xREC_ACCOUNT) = 1) then begin
          if NOT FillKES_for_Line_Created_ED(
                      aBudgetID,
                      xDoc195,
                      'KESR_HEAD_CODE',
                      '888',
                      aCfg_CreateParamAUBU,
                      'КОСГУ %s (в блоке  «Классификация получателя») не найден в БД')
            then xDoc195.SetAttribute( 'KESR_HEAD_CODE', '');
        end else begin
          xBDPD_KBK := GetNodeAttributeEx( aBDPD, 'KBK');
          // берем 3 последних символа BDPD.KBK, если поле >=3 символов
          // exchange #3081
          // здесь все по старому, только выпонена унификация кода
          if (LENGTH( xBDPD_KBK) >= 3) then
            if NOT FillKES_for_Line_Created_ED(
                        aBudgetID,
                        xDoc195,
                        'KESR_HEAD_CODE',
                        DoEncodeKBK_KES_or_KVR( xBDPD_KBK),
                        //COPY( xBDPD_KBK, LENGTH( xBDPD_KBK) - 2, 3),
                        aCfg_CreateParamAUBU,
                        'КОСГУ (из BDPD.KBK) %s (в блоке  «Классификация получателя») не найден в БД')
              then xDoc195.SetAttribute( 'KESR_HEAD_CODE', '');
        end;

        // Код субсидии	Не заполнять
        // КВФО	Если значение первых двух символов поля «Счет» блока «Получатель»
        // равно «21» или «31», то заполнять поле значением «9»,
        // иначе заполнять поле значением «8».
        if (COPY( xREC_ACCOUNT, 1, 2) in ['21','31'])
          then xDoc195.SetAttribute( 'FSR_HEAD_ID', '9')
          else xDoc195.SetAttribute( 'FSR_HEAD_ID', '8');

        // Отраслевой код	(реализация не меняется) ?
        // всегда должен быть после КВФО
        xDoc195.SetAttribute( 'INDUSTRYCODE_HEAD_ID',
                              DoSearch_INDUSTRYCODE_(
                                    GetNodeAttributeEx( xDoc195, 'FSR_HEAD_ID')));

        //------------------------------------------------------------------
        // exchange #3014 - поиск отр.кода с учетом учредителя
        // берем значение один раз из шапки и передаем его каждой строке.
        // если учредитель не указан - ищется без учета учредителя.
        // в этом случае, если код есть для уяредителя и для "не указан"
        // то код не будет найден.
        xOrgID := GetNodeAttributeEx( xDoc195, 'ORG_ID');

        //------------------------------------------------------------------
        // заполнение строк
        xDoc195Lines := xDoc195.appendChild(
                                         xXmlDoc195.createElement('LINES'));
        for i := 0 to aBDPD.childNodes.Length - 1 do
          if (aBDPD.childNodes.Item[i].NodeName = 'BDPDST') then begin
            xBDPDST := aBDPD.childNodes.Item[i];
            // новая строка в LINES в 195м
            xDoc195Line := xDoc195Lines.appendChild(
                                           xXmlDoc195.createElement('LINE'));
            // заполняем строку
            // exchange #3014 - поиск кода субсидии с учетом учредителя
            SetLineDoc195FromED_( xDoc195Line, xBDPDST, xOrgID);
          end;
        finally
          xIndustryCodes.Free;
      end;
      //------------------------------------------------------------------
      // Закладка «Документ-основание» - Не заполнять

      // создаем ЭД и переносим его на нужный статус
      //------------------------------------------------------------------
      // передаем документ на сервер, только если параметр проверки =false.

      // если проблем в строках нет, создаем эд как раньше.
      // если проблемы есть, проверяем параметр aCfg_CreateParamAUBU.
      // Вызывать метод формирования ЭД класса 193 вместо эд 5го
      CreateDoc_194_195_by_IK_Ex( aBudgetID,
                                  xDoc195,
                                  FALSE,    // эд 5й не создаем
                                  xProblems,
                                  aCfg_CreateParamAUBU,
                                  TRUE);      // создаем эд 193й
      except
        ExceptionProc( 'Create195_IK_BDPD_2965');
    end;

end;


begin
end.
