<?php // Полная загрузка сервисных книжек, создан 2025-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='\
use tempdb
CREATE TABLE myTable(FileName int,
Document varbinary(max))
GO
insert myTable(Filename,Document)
select 1,null
GO
UPDATE myTable
SET Document = (
SELECT *
FROM OPENROWSET(BULK ‘D:картинка14.jpg’, SINGLE_BLOB)AS x )
WHERE FileName = 1;
GO
select * from mytable
(1). Интересное решение. Не знал. А 1С как воспримет банные из varbinary?
ИМХО, все-таки правильнее было бы использовать не nvarchar-поле, а image…
кстати тогда получаем еще одно преимущество — можно хранить, например, различные документы (doc, .xls, .ppt, .txt, .html, .pdf,…), а для них можно применить индексирование с помощью фильтров и использовать full-text search для поиска по содержимому документов…
хранение в nvarchar этого кажись не позволит, ибо сказано было в документации: «Formatted text strings, such as Microsoft® Word™ document files or HTML files, cannot be stored in character string or Unicode columns because many of the bytes in these files contain data structures that do not form valid characters.»
(3). Я использую Base64Строка(Картинка.ПолучитьДвоичныеДанные()). А там можно любые двоичные данные в виде строки представить.
(4). Так это и понятно, но лучше бы как-нибудь без Base64… Искусственно размер увеличивается, во первых. Во вторых, если все таки хранить что нибудь типа документов, как я писал ранее, теряется возможность использования полнотекстового поиска по содержимому внутри сиквельной таблицы.
Можно попробовать через временные файлы… Типа так: StoredProc заводишь, которая содержимое image сливает в файл с заданным именем, а ты этот файл ДвоичнымиДанными…, и делаешь что нада… или же сразу картинку на основании файла сделать можно, если это картинка…
подобным образом сделал как то хранение документов, которые потом были доступны в 1с и одновременно с этим на сайтике… правда проект развития не получил, и все наработки непонятно где… скорее всего их и нет уже…
но вообще, для простых вещей конечно и так достаточно…
(5). Надо будет попробовать. Просто с Base64 вроде как понятнее.
Попробовал ложить в двоичном виде — ложить получилось, а вот с чтением проблемы, конструкция
выдает ошибку
Как побороть — понятия не имею. Если кто-то знает (без сохранения в промежуточный файл), просьба отпостить. Пока вижу единственный рабочий вариант с Base64Строка.
(3)тип Image
(8). Да-да. Байка про «неиспользование» типа image в будущих версиях есть и я это видел… действительно рекомендуется varbinary(max)… но в том числе и по личному опыту также знаю о различии в скоростях при работе с image и varbinary(max)…тынц
в принципе в 2008 есть уже и varbinary(max) filestream — можно поюзать его… вроде как это уже именно для подобных целей и будет оптимально с точки зрения производительности. сам не пробовал, руки не доходили, попробую как нибудь позже…
(7). Мало того, скорее всего то что залилось в базу — уже не картинка 🙁 …
(9). То есть на текущий момент лучше Base64Строка никто ничего работающего предложить не может…
ща, отобьюсь он назойливых… поеду домой, попробую сырцы поискать… sql какой? может правда на filestream переделать?
(9). То есть на текущий момент лучше Base64Строка никто ничего работающего предложить не может…
Можно, конечно использовать Stream, но здесь мы упираемся в необходимость сохранения файла на диск. В принципе, каждый из вариантов имеет свои плюсы и минусы, в мое случае плюс — это отсутствие необходимости вначале писать файл на диск, а минус — картинка занимает больше места, потому что вначале перекодируется с помощью Base64Строка.
Вариант с varbinary в данном случае полностью противоположный моему: необходимость сохранения картинки на диск перед тем, как ее прочитать в поле картинки, но картинка в базе будет занимать меньше.
(13). да никуда мы не упираемся… разум коллективный. эффект синергии… придумать можно чё нибудь…
Хранить файл в бд конечно хорошо но есть одно но УРБД.
Я считаю что можно воспользоваться моей компонентой по хранению
Преобразование картинки в строку
бинарных файлов в строке. Это лучше чем Base64Строка
компонента и обсуждение здесь
Может пригодится эта ссылка:Получение изображений, сохраненных в 1С:Предприятие 8.x, прямым доступом из SQL Server + пример кода на Asp.Net
(16). Немного не по теме. Здесь обсуждается не вытягивание картинки из базы 1С в стороннее приложение, а сохранение изображений в отдельной MSSQL базе непосредственно из 1С и чтение этих изображений непосредственно в 1С.
(13). н-да… нашел таки сырцы… ну и бред же я писал года полтора назад… 😉 шутка…
да все, естественно через файлы… отличие только в том что через OPENROWSET заливались сразу все доки в папке… а для чтения тот же стрим и в файл… стрим нужен был видимо для того чтоб на локальной машине сохранять…
но меня оправдывает то, что работа была именно с документами, а не с картинками, а там точно вариантов нет — только сохранение в темпарь… итак, дело в том, что тип COMSafeArray который ты получаешь на выходе с RecordSet.Fields(«…»).Value нада в виде типа Картинка получить… напрашивается что то типа ВК слепить по этому поводу… конечно если существует возможность тип Картинка или ДвоичныеДанные из нее вернуть… можно ли, не знаю…
(15). наверное от специфики проекта зависит… в конце концов РБД не везде. да и дело то не только в хранении, а прежде всего в доступе к внешней базе для получения двоичных данных без промежуточных поползновений по жесткому диску… это может быть просто база внешнего приложения, вполне независимого от1с… строка — хорошо, но недостаточно для меня было, т.к. нужно было и документы не испортить (которые в отдельной системе использовались) и в 1с их как то поиметь…
(18). Согласен, если нужно использовать эти файлы не только в 1С, тогда только в бинарном виде сохранять. У меня случай проще, мне нужно использовать файлы только в 1С 8, поэтому Base64 выглядит привлекательнее, не нужно пользоваться временными файлами.
Для решения задачи сохранения фотографий во внешней базе данных есть внешняя компонента «Фотоархив». Делалась для работы с фотографиями сотрудников в проекте учета рабочего времени. Работает под 7.7 и 8.1.
http://www.wbp-sar.ru/joomla/index.php?option=com_content&view=article&id=20:-qq&catid=12:2009-10-08-11-25-36&Itemid=37
База данных — SQL или файл Access (*.mdb). Можно использовать для сохранения любой информации, не только файлы с картинками. Например *.mp3 или *.doc. ВК сама создает базу данных в SQL и таблицу для сохранения. Можно задавать имя таблицы. Таблиц может быть сколько угодно.
Объект сохраняется и извлекается из базы по произвольно сформированному ID. В комплекте поставки пример привязки фотографий по внутреннему ID объекта в 1С.
Есть демо-версия
(20). 1) Сайт то-ли не работает полностью, то-ли о нем забыли.
2) Похоже ВК платная, тогда зачем платить деньги, если мой работающий пример бесплатный и тоже позволяет хранить любой файл.
3) Любая ВК требует регистрации ее с правами админа. Мой пример не использует ВК, поэтому будет работать сразу.
А будет он работать с базой на postgres ?
(22). Именно данная обработка нет, но если в ней переделать строку подключения и строки запросов под postgres, то, я уверен, оно заработает.
Всё бы не чего, но картинку большого размера не получится преобразовать в Строку (Base64Строка ) что делать? ((( есть выход?
(24). Большого — это какого? Я засовывал фотки 8-10 мегапикселей.
Размером более 50 мегабайт!
(26). Может просто долго пишется… Или ошибку выдает?
Именно ошибку выдает! говорить что слишком большой размер. приэтом пользовался всеми возможными методами преобразования в строку. не помогает! (
решил проблему следующим методом:
Stream=Новый COMОбъект(«ADODB.Stream»);
Stream.Type=1;
Stream.Open();
Stream.LoadFromFile(FileData1);
Спасибо огромное. помогла обработка!
Использовала данную обработку как основу для своей обработки. Очень полезная вещь, помогла очень. Спасибо!
(29), (30). У меня в профиле есть статья по хранению рисунков в базе без преобразования в Base64Строка. Работает быстрее и места в БД рисунки занимают меньше.
(28) Trakt0risT,
Можно по подробней, Вы строку передаёте потоком?
(22) alex_4x, (25)
Пытаюсь адаптировать для PostgreSQL. Преоброзование в Base64Строка файлов 8МБ проходит нормально, но при выполнении КомандаSQL.Execute(); либо ругаеться на надостаток памяти либо валиться платформа.
Вообще с Postgre очень странно работает. У меня, например, не работает выгрузка базы по расписанию. 1С просто вываливается с критической ошибкой. С MSSQL все нормально. Да и перестал я использовать 1С-ное поле картинки. Написал свою компоненту на C#, она и ложит рисунки в базу и отображает.
Пытался адаптировать под PostgreSQL несколько вариантов файловых хранилишь которые нашёл на infostart.ru всё закончилось неудачай. Хранить через Base64Строка единственное что удалось заставить работать и то толко для небольших файлов 🙁
а если тип данных в БД MySql Blob можно напрямую прочитать из 1С (без временного файла)?
Раз речь идет о MS SQL, то почему просто не пользоваться штатным механизмом файловых групп? И не нужно никакие сторонние базы создавать. Хочешь хоть каждый справочник или документ на отдельной дисковой подсистеме храни…
(36) Это Вы про какой штатный механизм упомянули? Что-то никто из моих коллег не в курсе…
(37) Механизм файловых групп позволяет разделить одну базу данных, на несколько физических файлов данных. Это позволяет разнести одну БД на отдельные дисковые массивы, что поможет решить проблему свободного места и/или производительности. Но, если мне не изменяет память, то при реструктуризации 1С создает копию таблицы, вносит в нее изменения, переносит данные, а затем, удаляет исходную. Создание происходит в дефолтной файловой группе. Таким образом, если я не ошибаюсь, то разделение внутри базы 1С живет до первого обновления, затрагивающего структуру метаданных.
(38) Silenser.
http://infostart.ru/public/77329/
Я понял. Вопрос был как раз в том, чтобы хранить картинки именно в отдельной базе. Кроме того, хранение в 1С-овской базе занимает, похоже, столько же места, сколько и в отдельной базе MSSQL с использованием Base64Строка, как описано в этой строке, поэтому именно этот механизм в моей конфе не используется, а используется вот этот
Можно немного подправить код на SQL и саму обработку, следующим образом: создать на SQL хранимую процедуру, которая будет принимать Base64 и перекодировать его обратно в binary и ложить в базу уже двоичные данные, а так же вьюшку, которая будет делать обратное преобразование. Кстати, вьюшку можно прицепить, как внешний источник данных и впоследствии данные выбирать простым запросом 1С. В коде в 1С соответственно поменять вызов Insert на вызов хранимой процедуры, а вместо select использовать либо вьюшку в запросе либо вьюшку, как связанный источник данных.