Загрузка изображений с Google.Картинки и Яндекс.Картинки (обычные формы)




Принцип обмена данными из 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='\

15 Comments

  1. premierex

    (0) Как можно улучшить функционал, не используя API поисковиков, а также временно «спрятать» свой забаненный IP за прокси-сервер можно посмотреть в этой обработке.

    P.S. Доступно только в полных версиях обработок.

    Reply
  2. Dmitriy_T

    (1) premier, Тратиться на вашу обработку — спасибо, перебьюсь. Есть предложения по улучшению — пишите в комменты открытым кодом, а проталкивать тут свою обработку, имхо, моветон.

    Также создалось устойчивое впечатление, что обработку вы не качали 😉 Будьте здоровы.

    Reply
  3. premierex

    (2) Размещать в комментах код на 12 страниц — вот это, имхо, моветон покруче, чем «проталкивать свою обработку». Спросили, как улучшить функционал Вашей обработки, я ответил: отказаться от IP поисковиков, добавить возможность посылать запросы через прокси. А ссылка на обработку приведена не для скачивания, а для ознакомления. Текст публикации и комментарии содержат, по моему мнению, ответы на вопросы по улучшению Вашей обработки.

    Также создалось устойчивое впечатление, что обработку вы не качали

    Нет, не качал — она мне ни к чему 😉 И Вам не хворать.

    Reply
  4. Dmitriy_T

    (3) premier, Будет интересно почитать 12 страниц кода, обязательно скачаю вашу обработку, тут их выкладывать не надо. А по существу, мне был бы интересен пример получения данных конкретно от Яндекса (любых данных) стандартными средствами (доступными простому обывателю, т.е. API-яндекса не предлагать), ну или хотя бы через общедоступную стороннюю компоненту, хочу уйти от использования АктивХ.

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

    Reply
  5. premierex

    (4) Попытаюсь кратко осветить мою технологию поиска на Yandex.

    Сначала я получаю ответ сервера GET запросом с URL https://yandex.ru/images/search?text=ВЫРАЖЕНИЕ_ПОИСКА&stype=image.

    Затем через встроенный объект 1С ПостроительDOM создаю объект ДокументHTML.

    После нормализации документа с ним можно работать как с DOM документом.

    На полученной странице меня заинтересовали элементы <div> с классом, содержащим класс «serp-item».

    Правда не все, а подходящие под условие регулярного выражения «serp-item serp-item_type_search serp-item_group_search serp-item_pos_d+ serp-item_theme_dark serp-item_series_no justifier__item i-bem».

    Затем я получаю фрагмент кода из атрибута «data-bem» элемента <div>, прошедшего проверку. Этот фрагмент определённым образом анализируется и, если содержит ссылку на изображение, загружается изображение по полученной ссылке.

    Вот, в общем, такой замысловатый алгоритм получился… Зато без использования API.

    Стороннюю компоненту «VBScript.RegExp» всё же пришлось использовать, потому как без регулярных выражений средствами одного только встроенного языка 1С довольно-таки затруднительно анализировать фрагменты текста (компонента, кстати, входит в дистрибутив поставки Windows и для её использования никаких расширенных прав пользователю не потребуется).

    По поводу прокси. Запросы через прокси отлично отрабатываются, а поскольку Yandex — не любитель автоматических запросов, частенько «банит» IP, с которого они приходят. И я уже не раз использовал соединение через прокси, чтобы скрыть свой IP. Ненадолго, правда, но прокси серверов достаточно много и, если уж хочется работать именно с Yandex адреса прокси просто можно менять после некоторого количества запросов, например.

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

    Reply
  6. Dmitriy_T

    (5) premier, Хм. Вроде все то же самое делаю (ну только без RegExp). Для Гугла прокатывает без проблем (ну может я его настолько не задолбал еще запросами, чтоб он меня банил), а вот Яндекс с лету меня шлет подальше (на этапе GET запроса). Если прокси это вылечит, тогда большое вам гранд мерси:) Я правильно понял — прокси нужно засунуть в параметры HTTPСоединения, чтобы вышло как-то так:

    …
    Прокси = Новый ИнтернетПрокси;
    Прокси.Установить(«https», <IP_Proxy>, <Port_Proxy>);
    СоединенияЯндекс = Новый HTTPСоединение(«yandex.ru»,,,,Прокси,,Новый ЗащищенноеСоединениеOpenSSL);
    …
    HTTPЗапрос = Новый HTTPЗапрос();
    ЗаголовкиЗапроса = Новый Соответствие;
    ЗаголовкиЗапроса.Вставить(«User-Agent»,ЮзерАгент);
    HTTPЗапрос.Заголовки = ЗаголовкиЗапроса;
    HTTPЗапрос.АдресРесурса = «/images/search?text=»+<ИскомаяКартинка>;
    ОтветHTTP = СоединенияЯндекс .Получить(HTTPЗапрос);
    Тело = ОтветHTTP.ПолучитьТелоКакСтроку();
    НовыйЧтение = Новый ЧтениеHTML;
    НовыйЧтение.УстановитьСтроку(Тело);
    ПостроительDOM = Новый ПостроительDOM;
    ДокументHTML = ПостроительDOM.Прочитать(НовыйЧтение);
    …

    Показать

    Reply
  7. premierex

    (6) да, примерно так. Меня сегодня трижды «банили». Через прокси тоже «банят», если сервер посчитает, что запросы идут слишком часто, но бесплатных прокси серверов множество. Так что для Yandex’a при редиректе на другую страницу можно смело из списка выбирать другой прокси, т.к. не раз замечал, что после «бана» Yandex производит редирект на страницу с капчой.

    Reply
  8. Dmitriy_T

    (7) premier, Как-то все равно не работает у меня. Делаю так:

    1) Получаю пачку проксей с HideMe.Ru

    2) Потом по этим проксям пробегаюсь и пробую создать HTTPСоединение и запросить заголовки по конкретному запросу в ожидании кода 200

    Для Каждого ТекПрокси Из ТабПроксей Цикл
    Прокси = Новый ИнтернетПрокси;
    Прокси.Установить(«https»,ТекПрокси.IP,ТекПрокси.Port);
    Соединение = Новый HTTPСоединение(АдресСервера, , , , Прокси,4,Новый ЗащищенноеСоединениеOpenSSL);
    …
    HTTPЗапрос.АдресРесурса = ТекстЗапроса;
    Попытка ОтветHTTP = Соединение.ПолучитьЗаголовки(HTTPЗапрос); Исключение Сообщить(ОписаниеОшибки()); Продолжить; КонецПопытки;
    Если ОтветHTTP.КодСостояния=200 Тогда
    …
    

    Показать

    3) Иногда (гораздо реже чем хотелось бы) мне это удается. Далее делаю полноценный запрос через найденный подходящий прокси. Как правило возвращается нормальный ответ (из которого можно выковырять нужные данные)

    4) Тут самое интересное. Делаю другой/такой же (без разницы) запрос к этому же соединению (через тот же прокси) спустя некоторое время — получаю от Яндекса редирект на КАПЧУ в 98% случаев.

    Т.е. получается — получил, проверил, а работать дальше не могу — надо искать заново и так до поседения.. Что делаю не так?

    После того как написал, напоролся на прокси, который пару раз таки отработал. Возникло подозрение, что у меня какие-то не такие прокси. Подскажите, плиз, где взять «правильные»?

    Reply
  9. premierex

    (8) а я же писал в (7), что «банят» и через прокси. Особенно, как я заметил, европейские (чаще всего российские). Хотя, Yandex’у, мне, кажется, всё равно, какой прокси используется. Скорее всего, измеряется частота запросов и интервал между их повторениями. Я для примера протестировал несколько прокси-серверов из того же списка, что и Вы указали. Чем меньше скорость отклика прокси-сервера, тем больше вероятность «бана». И вообще, создается впечатление, что список прокси с сайта http://hideme.ru/proxy-list уже внесен в «черный» список Yandex. Хотя, если хоть один запрос «прокатывает», можно просто случайным методом подставлять прокси для каждого запроса. Или взять список прокси с другого сайта, хотя, вероятность дублирования серверов достаточно велика. Что интересно, Yandex и Rambler при поиске выдают примерно одинаковые результаты. Похоже, что поисковый движок один и тот же используется (из 10 полученных изображений — 9 похожи как близнецы). Поэтому, как вариант обхода ситуации с Yandex, я, например, включил в список поисковых серверов ещё и Rambler. С него ни одного «бана» ущё не получил.

    Reply
  10. premierex

    (8) 2) Потом по этим проксям пробегаюсь и пробую создать HTTPСоединение и запросить заголовки по конкретному запросу в ожидании кода 200 .

    Кстати, я бы не стал ограничиваться ожиданием заголовка со статусом 200 в ответе сервера. См. эдесь. Другие заголовки, чьи статусы меньше 300, часто носят информативный характер, но ответ на запрос всё же возвращают.

    Reply
  11. Dmitriy_T

    (10) premier, Картинки — это ж баловство на самом деле. Интересен в частности Маркет, а его на Рамблере не найдешь. Пока вариантов кроме АктивХ элемент браузера на форме у меня нет, но это ж как-то некрасиво что ли)) Про коды кроме 200 — спасибо, просветился.

    Reply
  12. premierex

    (11) картинки — это, конечно же, не баловство. Я думаю, есть масса пользователей, которым «влом» выдёргивать картинки из интернета вручную и вставлять в 1С. Поэтому, считаю, что автоматизация такого рутинного процесса необходима многим. Да и в анонсе Вашей публикации явно указано «Загрузка изображений с Google.Картинки и Яндекс.Картинки». Всё же КАРТИНКИ!

    Маркет — тема совсем другой публикации. Но, как правило, «маркет» (я так думаю, это — Интернет-магазин), точнее сайты, предоставляющие такой сервис, требуют от пользователя интерактивных действий, т.е. данные загружаются в динамическом режиме и анализировать содержимое контента такого сайта зачастую бывает просто невозможно без API, участия пользователя, использования встроенного (или стороннего web-browsera) и т.д. Автоматизация в этом случае = 0. Может, я и ошибаюсь.

    P.S. Во многих публикациях замечал, что они закрывались потому, что предложенные в них обработки использовали API поисковых систем, которые производители объявляли как «deprecated», т.е. устаревшими и более не поддерживаемыми.

    Reply
  13. avtax

    Большое человеческое спасибо за обработку

    Reply
  14. Murom

    Скачал эту обработку и другую обработку автора, который тут тоже отписывался.

    Эта обработка работает. Картинки сканирует. Автору однозначно спасибо за работу!!!

    В чем плюс по сравнению с другой обработкой, которая тут обсуждалась (не хочу писать название, чтоб не сочли за рекламу), так это в кнопочке «->» — типа найти следующие. Так же обработка находит картинки на google с возможностью выбора разного размера.

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

    Себе в работу взял все-таки другую обработку, но вставил туда загрузку картинок из google из этой обработки.

    Reply
  15. antonius888

    Не работает 🙁 Похоже, что проблема во взаимодействии обработки с APi гугла и яндекса

    Reply

Leave a Comment

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