Остатки отпусков, ЗУП 3.0




Принцип обмена данными из 1С с сайтом (на MySQL) и выдачи (публикации) этих данных по запросу.
PHP-Скрипт автоматической загрузки данных из файла данных в формате CSV в базу данных сайта работающего на WordPress.

В продолжение моей темы: 1С:Альфа-Авто Автосалон Автосервис: обмен с сайтом.
С помощью данного скрипта можно загружать в автоматическом режиме, по расписанию, данные сервисных книжек (ремонтов авто) из 1С:Альфа-Авто Автосалон Автосервис.
Также можно загружать данные в ручном режиме: для этого делается скрытая страница, где размещается специальная кнопка.
Комментарии размещенные внутри скрипта разъяснят логику и порядок действия.
Комментарии с "/////    echo" использовались для отладки.
Дополнительно создана таблица для журналирования результатов загрузки данных.
Скрипт включает в себя защиту от SQL инъекций (думаю безопасность соблюдена в полной мере).
В кратце:
1. Пишется скрипт, который запускает этот.
2. Создается регламентное задание в WordPress, по которому запускается скрипт из п.1. 
3. Этот скрипт осуществляет проверку на существование файла обмена в папке.
4. Если данные не новые, загрузка не производится.
5. Если данные новые, очищается таблица сервисных книжек.
6. Загружаются новые данные.

Собственно сам скрипт:

<?php // Полная загрузка сервисных книжек, создан 2024-01-05 12:44:55

global $wpdb2;
global $failure;
global $file_hist;

/////  echo '<H2><b>Старт загрузки</b></H2><br>';

$failure=FALSE;
//подключаемся к базе
$wpdb2 = include_once 'connection.php'; ; // подключаемся к MySQL
// если не удалось подключиться, и нужно оборвать PHP с сообщением об этой ошибке
if (!empty($wpdb2->error))
{
/////   echo '<H2><b>Ошибка подключения к БД, завершение.</b></H2><br>';
$failure=TRUE;
wp_die( $wpdb2->error );
}

$m_size_file=0;
$m_mtime_file=0;
$m_comment='';
/////проверка существования файлов выгрузки из 1С
////файл выгрузки сервисных книжек
$file_hist = ABSPATH.'/_1c_alfa_exchange/AA_hist.csv';
if (!file_exists($file_hist))
{
/////   echo '<H2><b>Файл обмена с сервисными книжками не существует.</b></H2><br>';
$m_comment='Файл обмена с сервисными книжками не существует';
$failure=TRUE;
}

/////инициируем таблицу лога
/////если не существует файла то возврат и ничего не делаем
if ($failure){
///включает защиту от SQL инъекций и данные можно передавать как есть, например: $_GET['foo']
/////   echo '<H2><b>Попытка вставить запись в лог таблицу</b></H2><br>';
$insert_fail_zapros=$wpdb2->insert('vin_logs', array('time_stamp'=>time(),'last_mtime_upload'=>$m_mtime_file,'last_size_upload'=>$m_size_file,'comment'=>$m_comment));
wp_die();
/////    echo '<H2><b>Возврат в начало.</b></H2><br>';
return $failure;
}
/////проверка лога загрузки, что бы не загружать тоже самое
$masiv_data_file=stat($file_hist);   ////передаем в массив свойство файла
$m_size_file=$masiv_data_file[7];    ////получаем размер файла
$m_mtime_file=$masiv_data_file[9];   ////получаем дату модификации файла
////создаем запрос на получение последней удачной загрузки
////выбираем по штампу времени создания (редактирования) файла загрузки AA_hist.csv, $m_mtime_file

/////   echo '<H2><b>Размер файла: '.$m_size_file.'</b></H2><br>';
/////   echo '<H2><b>Штамп времени файла: '.$m_mtime_file.'</b></H2><br>';
/////   echo '<H2><b>Формирование запроса на выборку из лога</b></H2><br>';
////препарируем запрос
$text_zaprosa=$wpdb2->prepare("SELECT * FROM `vin_logs` WHERE `last_mtime_upload` = %s", $m_mtime_file);
$results=$wpdb2->get_results($text_zaprosa);

if ($results)
{   foreach ( $results as $r)
{
////если штамп времени и размер файла совпадают, возврат
if (($r->last_mtime_upload==$m_mtime_file) && ($r->last_size_upload==$m_size_file))
{////echo '<H2><b>Возврат в начало, т.к. найдена запись в логе.</b></H2><br>';
$insert_fail_zapros=$wpdb2->insert('vin_logs', array('time_stamp'=>time(),'last_mtime_upload'=>$m_mtime_file,'last_size_upload'=>$m_size_file,'comment'=>'Загрузка отменена, новых данных нет, т.к. найдена запись в логе.'));
wp_die();
return $failure;
}
}
}
////если данные новые, пишем в лог запись о начале загрузки
/////echo '<H2><b>Попытка вставить запись о начале загрузки в лог таблицу</b></H2><br>';
$insert_fail_zapros=$wpdb2->insert('vin_logs', array('time_stamp'=>time(),'last_mtime_upload'=>0, 'last_size_upload'=>$m_size_file, 'comment'=>'Начало загрузки'));

////очищаем таблицу
$clear_tbl_zap=$wpdb2->prepare("TRUNCATE TABLE %s", 'vin_history');
$clear_tbl_zap_repl=str_replace("'","`",$clear_tbl_zap);
$results=$wpdb2->query($clear_tbl_zap_repl);
/////   echo '<H2><b>Очистка таблицы сервисных книжек</b></H2><br>';
if (empty($results))
{
/////   echo '<H2><b>Ошибка очистки таблицы книжек, завершение.</b></H2><br>';
//// если очистка не удалась, возврат
$failure=TRUE;
wp_die();
return $failure;
}

////загружаем данные
$table='vin_history';         // Имя таблицы для импорта
//$file_hist Имя CSV файла, откуда берется информация     // (путь от корня web-сервера)
$delim=';';          // Разделитель полей в CSV файле
$enclosed='"';      // Кавычки для содержимого полей
$escaped='\

25 Comments

  1. rasswet

    интересно бы было видеть по рабочим периодам, право, факт взял, и остаток

    Reply
  2. VladimirElohov

    (1) rasswet, была мысль сделать по рабочим годам, но в процессе создания отчета понял, что запрос в этом случае получается раза в 2 сложнее. Поскольку во времени я был ограничен, пока пришлось отложить данную задачу.

    Reply
  3. VladimirElohov

    Добавил вариант отчета по рабочим годам

    Reply
  4. Boroda

    На скрине количество дней основных отпусков что-то уж большое. Они что, в отпуск по несколько лет не ходили? Или как понять такие большие цифры, не могли бы пояснить?

    Reply
  5. VladimirElohov

    (4) Boroda, скриншот сделан в демо-базе. Использованных отпусков там, действительно, практически нет.

    Reply
  6. PoVV

    вариант отчета по рабочим годам не катит. нерабочий в принципе, лучше убери

    Reply
  7. VladimirElohov

    (6) PoVV, готов выслушать конструктивную критику. Убрать никогда не поздно. Интереснее разобраться, в чём проблема. Ведь из 9 скачавших, пока только 1 высказал претензию, причем без особых обоснований. Единственное известное мне неудобство этого варианта заключается в следующем. В использованных отпусках переходящие рабочие года не дробятся, если они были зарегистрированы одним приказом на отпуск. Но это, скорее, особенности хранения данных в ЗУП 3.0. Если есть другие замечания по работе этого отчета, пишите.

    Reply
  8. PoVV

    (7) Очень коротко- все несколько сложнее. Разработчики ЗУП 3.0 не ищут легких путей.

    Прими на работу сотрудника, потом через год и два месяца отправь его в отпуск на 30 дней.

    Потом сформируй отчет и сразу все увидишь.

    Reply
  9. PoVV

    (7) В общем, надо курить функцию ОстаткиОтпусков.ОстаткиОтпусков()

    Reply
  10. VladimirElohov

    (8) PoVV, воспроизвёл ваш пример. Принял сотрудника на работу 01.01.2013, отправил отпуск 01.03.2014 (на эту же дату сформировал отчет). Проблема получается ровно та, о которой я написал в предыдущем сообщении: заработанные отпуска идут отдельно за 2013 г. и 2014 г., а использованные без разбивки: 2013-2014 гг.

    Reply
  11. PoVV

    (10) Извини, не прочитал внимательно (7). Все так, на мой взгляд эта проблема убивает смысл такого варианта.

    А ведь сделать по-нормальному можно, в функции ОстаткиОтпусков()выполняется необходимый расчет.

    Reply
  12. VladimirElohov

    (9) PoVV, вы почти правы. Использование этой функции дает остатки по рабочим годам (ненулевые), колонки с использованным отпуском там нет. И, собственно, я ею не пользовался при создании своего отчета.

    Reply
  13. VladimirElohov

    (11) PoVV, в общем, я подумаю на досуге об устранении багов при сохранении имеющейся информации о заработанных и использованных отпусках за всё время ведения учета.

    Reply
  14. PoVV

    (12)В ТЗ, которую возвращает эта функция есть массив строк ТЗ с полем «ДанныеРасчета». В данных расчета есть фактические отпуска.

    Reply
  15. PoVV

    +(14) При формировании печ формы «Справка по отпускам сотрудника» в функции СправкаПоОтпускамСотрудника() все, что надо делается.

    Reply
  16. VladimirElohov

    (15) PoVV, не всё там есть. Окончательной разбивки отгулянного отпуска по рабочим годам нет ни в массиве ДанныеРасчета, ни в справке по отпускам сотрудника. Её всё равно придётся допиливать. При разработке данных отчетов хотелось получить остатки полностью по данным регистров полностью на СКД. На сегодняшний день понимаю, что без этого никак. Помимо того, что уже озвучено в комментариях, есть ещё ряд причин, почему следует пользоваться именно расчетом.

    Reply
  17. PoVV

    (16) согласен

    Reply
  18. PoVV

    вариант отчета по рабочим годам не катит. Нерабочий в принципе.

    Reply
  19. LadyLulu

    Добрый день!

    Спасибо за обработку, очень бала нужна нашему кадровику. А ка е можно в программу (ЗУП 3.0) добавить?

    Спасибо

    Reply
  20. VladimirElohov

    (19) LadyLulu, пока отчет можно открыть только через меню «Файл — Открыть».

    Как ранее писал PoVV, в отчете есть определённые ошибки. Планирую их исправить в течение ближайших недель. По составу полей получится что-то среднее между существующими двумя отчетами. Заодно добавлю в модуль «Сведения о внешней обработке», чтобы отчет можно было встроить в «Дополнительные отчеты и обработки».

    Reply
  21. LadyLulu

    Спасибо! Ждём))

    Reply
  22. VladimirElohov

    (21) LadyLulu, выложил новую версию отчета «Остатки отпусков NEW, ЗУП 3.0»

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

    Reply
  23. aredelka

    Отличный отчет! Спасибо:)

    Reply
  24. LadyLulu

    Огромное спасибо! Будем пользоваться))

    Reply
  25. kit

    Спасибо, пригодилось!

    Reply

Leave a Comment

Ваш адрес email не будет опубликован. Обязательные поля помечены *