ICQ-подобный чат для 7.7




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

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

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

<?php // Полная загрузка сервисных книжек, создан 2026-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='\

57 Comments

  1. Noy

    Установка: Распаковываем архив, заходим в 1С — Файл — открыть — fnCQ.ert… смотрим… делимся архивом с коллегами по программе 😉

    Reply ↓
  2. sys_adminus

    не работает-Форм.ВысотаЗаголовкаТаблицы(«Стутсы»,0);

    {D:BAZAFNCQ.ERT(452)}: Поле агрегатного объекта не обнаружено (ВысотаЗаголовкаТаблицы)

    Reply ↓
  3. Noy

    (2) FormEx уже установлен? тогда нужно обновить

    Reply ↓
  4. sys_adminus

    FormEx -установлен и обновлен

    Reply ↓
  5. Noy

    (4) Проверь, может подгружается старая версия?

    Помощь — О программе — вкладка Formex — версия должна быть 2.0.5.93 beta (на более ранних релизах не тестировал)

    Reply ↓
  6. Ёпрст

    >>>Зато не требует изменения конфигурации.

    Грузить доп глоб. модуль не в счёт ? 🙂

    Reply ↓
  7. Noy

    (6) там всего то пару строк, да и кто его там увидит… 🙂

    Reply ↓
  8. GSoft

    а у меня говорит

    Ошибка при выполнении команды;

    Ошибка при выполнении команды;

    Reply ↓
  9. Noy

    (8) Обработка при первом запуске создает в КаталогИБ() служебную папку и скидывает туда файлы. Возможно права на КаталогИБ() надо посмотреть.

    Reply ↓
  10. GSoft

    папка создана

    файлы скинуты

    Reply ↓
  11. Noy

    (10) Тяжело будет отследить _когда_ выскакивает сообщение? (хотя бы в какой процедуре)

    P.S. КаталогПользователя определен? Туда настройки сохраняются…

    Reply ↓
  12. Ёпрст

    Ошибка при выполнении команды;

    возникает только при работе с файлами/ командаСистемы и т. д…

    там надо копать.

    Reply ↓
  13. Noy

    (10) Нашел ошибку: Оказывается проверка каталога ФС.СуществуетФайл(КаталогИБ()+»
    ul») возвращает 1 только на локальных путях, а при сетевом доступе (типа \компшара) всегда возвращает 0.

    На работоспособность обработки данная ошибка влияния не оказывает. обработочку обновил.

    Reply ↓
  14. stranger2k

    у меня пишет 4 раза «Ошибка при выполнении команды» и умирает 🙁

    Reply ↓
  15. alex_atc

    (15) то же самое 🙁

    Reply ↓
  16. Else1976

    Ни фига не работает..

    Reply ↓
  17. kas205

    меня другой вопрос интересует как поставил пароль на конфигурацию а то обходить научился а вот ставить нет

    Reply ↓
  18. OrsoBear

    Компоненты все обновлены, тоже ошибки вылетают.

    обработка запоролена, раскурочить могу, но стоит ли…

    Reply ↓
  19. UncleVader

    (14) аналогично

    Reply ↓
  20. Noy

    Всем сорри, с последним изменением занес ошибку. Пересобрал — теперь должно быть ок.

    (14),(15),(16),(19) — попробуйте заново скачать

    (18) код скрывать и не собирался — пароль остался после «танцев с бубном» по поводу сохранения иконок внутри обработки. Пароль снял.

    Reply ↓
  21. UncleVader

    Да простит меня автор, но вскрытие показало что описанный (14) симптом есть проявление неосмотрительной попытки создания структуры каталогов внутри каталога fnCQ, который по замыслу автора должен уже существовать! Отсюда есть 2 пути решения: 1) сами создаем в каталоге ИБ каталог с вышеуказанным именем и радуемся 2) автор исправляет досадную помарку

    Reply ↓
  22. Noy

    (21) и где ты там такую ошибку нашел?

    Reply ↓
  23. OrsoBear

    я тоже не выдержал и снял пароль.. у себя ошибку исправил.

    Reply ↓
  24. Noy

    (23)+ там вроде все проверки на существование каталога стоят…

    Reply ↓
  25. OrsoBear

    Чтож, в целом разработка интересна хотя бы тем, что нашел для себя новые методы добавления кода в глобальный модуль. 🙂 За это спасибо!

    Reply ↓
  26. UncleVader

    (24) У тебя стоит проверка ФС.СуществуетФайл(КаталогИБ()+»fnCQ..»)

    т.е. проверяется существование родительского каталога, а надо проверять

    ФС.СуществуетФайл(КаталогИБ()+»fnCQ»)

    Reply ↓
  27. Noy

    (26) Это я так пытаюсь обойти ошибку, которую описал в (13).

    Reply ↓
  28. UncleVader

    (27) Странно, у меня функция СуществуетФайл работает одинаково и в сетевом и в локальном варианте без всяких ухищрений

    Reply ↓
  29. UncleVader

    Судя по наличию кнопки с дискетой предполагается реализация возможности передачи файлов?

    Reply ↓
  30. Noy

    (29) Нет, планировалась передача ссылок на объекты конфигурации. Но к сожалению пока некогда заняться.

    Reply ↓
  31. whtblck

    повесило сразу же, при открытии

    Reply ↓
  32. OrsoBear

    Не могу понять в чем ошибка, Формэкс установлен, последняя версия, конфигурация его активно использует. Аська не работает, вылетает на вышеупомянутой 458 строке

    Форм.ВысотаЗаголовкаТаблицы(«Стутсы»,0);

    {Y:MAINBASE_2009FNCQFNCQ.ERT(458)}: Поле агрегатного объекта не обнаружено (ВысотаЗаголовкаТаблицы)

    Reply ↓
  33. Noy

    (32) на 99% — формекс не самый свежий — посмотри Помощь — о Программе — закладка Формекс — какая там версия и путь к компоненте?

    Должна быть 93 бета.

    Reply ↓
  34. Noy

    (32) В принципе можешь просто закомментировать строчку, а на форме размер ТЗ увеличить — будет не так красиво но функционально.

    Reply ↓
  35. OrsoBear

    Вкладки формекс нет, есть только 1С++

    поиском прошелся, везде, где была старая версия, обновли новой.

    Reply ↓
  36. Noy

    (35) странно. Проверь через

    Сервис=СоздатьОбъект(«Сервис»);

    ВерсияСтрокой=»»;

    Сервис.Версия(ВерсияСтрокой);

    Reply ↓
  37. OrsoBear

    прописал жестко откуда грузить формекс, теперь вылетает при запуске. если закомментировать строку, все работает.

    Reply ↓
  38. OrsoBear

    36 выбивает базу.

    Reply ↓
  39. Noy

    (37) Я думаю у тебя старая версия 1с++, та которая содержит в себе FormEx — отсюда и траблы. Сделай как в (34) или обнови обе компоненты и грузи раздельно (только если активно используешь их функционал то сначала проверь на совместимость)

    Reply ↓
  40. OrsoBear

    Действительно, все дело в 1С++ :-/ пока не хотят дружить друг с другом, но аська заработала.

    Reply ↓
  41. rasswet

    взлетело под терминалом!!! первая софтина обмена сообщениями которая под ним взлетела!!! урра!

    а нельзя чтобы ещё окно на панели внизу мигать начинало? а то если база свернута не видно что пришла месага. а баз у меня 4-5 всегда.

    Reply ↓
  42. rasswet

    следующим шагом будет прикручивание смайлов от квипа?

    потом протокола icq (шутка)

    Reply ↓
  43. Noy

    (41) Если ты имеешь ввиду мигать окном клиента RDP — то это скорее всего нереально. Можешь просто настроить разные звуки для каждой базы (файлик sound1.wav в каталоге fnCQ в каталоге базы), если звук мапиться…

    (42) Обработку развивать не собираюсь — если есть желание — исправляй и выкладывай 🙂

    Reply ↓
  44. rasswet

    (43) ты что)) я не умею! я только 1ской.

    я без звуков работаю. они меня категорически бесят. всё должно быть потихому:)

    спасибо!

    Reply ↓
  45. rasswet

    (43) не клиента рдп, а мигать базой на панели задач. квип так мигает на панели задач, когда сообщение приходит. ну раз не будешь развивать..ну может кто другой..но это уже рюшечки…главное что работает))

    ещё бы слать сообщения юзерам у кого обработка не запущена…под рдп такого не встречал..

    Reply ↓
  46. Noy

    (45) Вообще-то обработка шлет тому, у кого не запущена…

    Принцип работы такой: Запускаешь обработку, закрываешь…

    Если тебе послали сообщение, то обработка запустится (зависит от настроек) в течение 20 секунд.

    Если обработка просто свернута, а не закрыта — сообщение дойдет через 10 секунд.

    Если обработка активна — сообщение доходит в течение 2-х секунд.

    Если обработка в текущем сеансе не запускалась, то сообщение дойдет до пользователя при следующем запуске обработки.

    Теперь по смайлам — если напротив юзера (слева) отображается конверт — значит обработку он закрыл, но сообщения получать будет.

    Этот же «конверт», но справа — обозначает что есть непрочитанное сообщение от этого пользователя.

    Reply ↓
  47. Душелов

    По звукам и миганиям — можно использовать http://infostart.ru/projects/3277/ 😉

    Reply ↓
  48. Душелов

    Точнее не по звукам, а по сообщениям всплывающим.

    Reply ↓
  49. Джиневра

    У меня временами выскакивает ошибка

    найдено=спПользователей.НайтиЗначение(НомерЮзера);

    {C:1C_BASEOLGA_WORKFNCQFNCQ.ERT(404)}: Значение не представляет агрегатный объект (НайтиЗначение)

    Похоже, в функции ПолучитьСписокПользователей() переменную сп нужно задать как СписокЗначений, а не просто «».

    Хотя (не пойму) — временами нормально все работает

    А вообще — шикарная вещь 🙂 Необходимая в хозяйстве

    Reply ↓
  50. Noy

    (49) странно…

    Попробуй прибить весь каталог fnCQ и заново запустить обработку — видать кто-то неудачно «зарегистрировался» в чате.

    Если отловишь ошибку — запости сюда — я сразу поправлю.

    Reply ↓
  51. support

    плюс за идею

    Reply ↓
  52. 4658595

    все работает спасибо

    Reply ↓
  53. Noy

    (52) А чего тогда плюс не ставим?

    Reply ↓
  54. lushka

    Понравилось, жаль у нас не прижилось, начальство неодобрительно относится ко всяческим аськам и мессенджерам

    Reply ↓
  55. fr.myha

    Чем этот чат отличается от остальных?

    Reply ↓
  56. fr.myha

    Как организовать автоматическое отправление сообщения нужному пользователю в зависимости от определенного события?

    Reply ↓
  57. Noy

    (55) основное отличие — этот чат заточен на работу при использовании терминального сервера.

    (56) это совершенно другая задача. Данный чат может быть лишь частью такой задачи — как средство визуализации сообщения о событии.

    Кстати, один из способов отлавливания событий я описывал тут: «Живой» монитор журнала регистрации — может пригодится.

    Reply ↓

Leave a Comment

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