WinHttpRequest/ServerXMLHTTP - а теперь, как отправить zip?

1. zhenyat 6 13.02.23 13:21 Сейчас в теме
И снова все доброго дня!
Преамбула:
Долгое время для интернет-магазина использовали битрикс, на своем сервере. И свою самописную обработку для обмена 1с 7.7 (опять же кастомная конфа) для обмена с ним. Написана она была с использованием v7plus. Битрикс, из-за старенькой ОС (CentOS 6.5) уже не мог обновляться, а перенести магазин на новый через архив - не получилось, из-за разработчиков конкретно нашего магазина, как то так криво адаптировавших выбранный шаблон под наши хотелки, что новом движке битрикса у него вылетало все что только можно с руганью о устаревших и неподдерживаемых операторах.
Но вот так случилось что сервер с битриксом скоропостижно скончался, и прежде чем его восстанавливать, решила я оглядеться - а что за эти годы (около 10) изменилось? Может появилось что-то поинтереснее и полегче битрикса?
Ну вот обратила внимание на InSales - и выглядит симпатично, и легкая, и обмен с 1с по тому же протоколу, что и у битрикса. Но вот беда - у InSales обмен возможен только по протоколу https, который v7plus не поддерживает.
Делать нечего, засучила рукава, стала переделывать на использование системных компонент, на выбор - либо WinHttpRequest, - либо ServerXMLHTTP.
Теперь собтвенно проблема:
С приёмом данных от вебсервера справилась. С передачей xml тоже. Засада появилась при попытке передать zip файл.

В v7plus все проблемы по формированию заголовков и правильной обертке данных для передачи берет на себя сама компонента. Пишешь просто
Соединение.ОтправитьДляОбработки(Ресурс + "?type=sale&mode=file&filename=" + ФайлЗаказов, ПутьКЗаказам, 1, Ответ, 2)

в ФайлЗаказов - имя файла
в ПутьКЗаказам - полный путь к файлу
И не важно что там в файле, xml или zip - 1с файл отправит, вебсервер его примет
А вот с компонентами всё на так просто :(
Ладно, как я уже говорила, с текстом (xml) я справилась:
Функция ОтправитьДляОбработки(Соединение, Ресурс, Знач Источник, ТипДанных, Ответ, ТипОтвета)  
	
	//ТипДанных = 1 - Путь к файлу, 2 - Строка, 3 - поток
	//ТипЩтвета = 1 - Путь к файлу, 2 - Строка, 3 - поток
	
	Если флДвижок = 1 Тогда
		Соединение.Open("POST", Ресурс, 0, ПараметрыСоединения.ИмяПользователя, ПараметрыСоединения.ПарольПользователя);
	Иначе
		Соединение.Open("POST", Ресурс, 0);
		Соединение.SetCredentials(ПараметрыСоединения.ИмяПользователя, ПараметрыСоединения.ПарольПользователя, 0);
	КонецЕсли;
		
	Если ПустоеЗначение(ПараметрыСоединения.Печенька) = 0 Тогда
		Соединение.SetRequestHeader("Cookie", ПараметрыСоединения.Печенька);
	КонецЕсли;

	
	Если ТипДанных = 1 Тогда
		
		Если Прав(Источник, 3) = "xml" Тогда
			
			ДанныеДляОтправки = СоздатьОбъект("MSXML2.DOMDocument.6.0");
			ДанныеДляОтправки.load(Источник);
			
			Соединение.Send(ДанныеДляОтправки.xml)
			
		Иначе
			
		КонецЕсли;
									
	Иначе
		
		Соединение.Send(Источник);
		
	КонецЕсли;
			
	Если Соединение.Status <> 200 Тогда
		Предупреждение(Ресурс + РазделительСтрок + Соединение.Status + " " + Соединение.statusText);
		Возврат 0;
	КонецЕсли;
	
	Если ТипОтвета = 1 Тогда
		
	ИначеЕсли ТипОтвета = 2 Тогда
		
		Ответ = СтрЗаменить(Соединение.ResponseText, Симв(13), "");
		Ответ = СтрЗаменить(Ответ, Симв(10), РазделительСтрок);

	Иначе

		Ответ = Соединение.ResponseStream;
		
	КонецЕсли;	
	
	Возврат 1;

КонецФункции
Показать


А вот с zip - возникли проблемы.
Попыталась использовать 1cpp BinaryData:
ДвоичныеДанные = СоздатьОбъект("BinaryData");
ДвоичныеДанные.ЗагрузитьИзФайла(Источник);
			
РазмерФайла = ДвоичныеДанные.Размер();
ДвоичныеДанные.Перейти(0, 0);

ДанныеДляОтправки = 0;
ДвоичныеДанные.ПрочитатьСтроку(ДанныеДляОтправки, РазмерФайла);
Соединение.Send(ДанныеДляОтправки);
Показать

Ошибка "Недопустимая длина."


Пробовала ADODB.Stream - тоже не получается:
Поток = СоздатьОбъект("adodb.stream");
Поток.Mode = 1;
Поток.Open();
Поток.LoadFromFile(Источник);
Соединение.Send(Поток.Read(Поток.Size));

1c ругается - мол Read() возвращает неподдерживаемый тип

И я опять в тупике - как же отправить то файл?
Найденные решения
9. zhenyat 6 17.02.23 19:08 Сейчас в теме
Все оказалось до тривиального просто

Поток = СоздатьОбъект("adodb.stream");
Поток.Type = 1;
Поток.Open();
Поток.LoadFromFile(Источник);
		
Если Найти(Источник, ".jpg") > 0 Тогда
	Соединение.setRequestHeader("Content-Type", "image/jpeg");
ИначеЕсли Найти(Источник, ".zip") > 0 Тогда
	Соединение.setRequestHeader("Content-Type", "application/zip");
ИначеЕсли Найти(Источник, ".xml") > 0 Тогда
	Соединение.setRequestHeader("Content-Type", "application/xml;charset=utf-8");
КонецЕсли;
	
Соединение.Send(Поток);
Поток.Close();
Показать
Остальные ответы
Подписаться на ответы Сортировка: Древо развёрнутое
Свернуть все
7. spacecraft 15.02.23 20:09 Сейчас в теме
(1) а что, api.insales.ru не подходит?
Там же подробно описано, как передавать файл.
https://api.insales.ru/?_ga=2.19129851.2121637265.1676480380-686589007.1675529000#file-create-file-from-attachment-json
2. user1880116 13.02.23 14:21 Сейчас в теме
у InSales обмен возможен только по протоколу https, который v7plus не поддерживает
Дык поставь https прокси и заверни в него все то, что работало через v7plus
3. CheBurator 3119 14.02.23 21:06 Сейчас в теме
там скорее всего как-то перекодировать надо в басе64 возмождно и указывать правильный заголоовк.
.
какими нить сторонними средствами отправить аналогичный запрос и какимнить монитором отследить пакет который формируется
5. zhenyat 6 15.02.23 16:34 Сейчас в теме
(3) Я SoapUI пробовала, атачем пристегнуть к post запросу, но почему то файл на сайте сохранялся вместе с "заголовком" boundary
А если просто пихать двоичное содержимое файла архива в тело - почему то байты 0х00 в файле заменяются на 0х20, возможно неправильно укfзываю тип содержимого - application/zip?
4. CheBurator 3119 14.02.23 21:06 Сейчас в теме
можно тупо через CURL попробовать.
и потом взять curl1c
6. zhenyat 6 15.02.23 16:37 Сейчас в теме
(4)curl у меня на сервере есть, я дажа принимаю им файлы со своего другого веб-сервера, но там вся безопасность - тупо нестандртный порт ресурса и входящие разрешены только с одного адреса - адреса 1с сервера.

Но я в нем не сильна :( Как в параметры curl вставить в заголовок куку и авторизацию?
8. CheBurator 3119 15.02.23 21:37 Сейчас в теме
и входящие разрешены только с одного адреса - адреса 1с сервера.
- ну ставишь курл на сервере1
.
а далее я сам слабоват ;-)
в принципе там формируешь запрос нужного формата правильно оформленный и курл его пихает и возвращает ответ.
надо доки по курлу читать...
9. zhenyat 6 17.02.23 19:08 Сейчас в теме
Все оказалось до тривиального просто

Поток = СоздатьОбъект("adodb.stream");
Поток.Type = 1;
Поток.Open();
Поток.LoadFromFile(Источник);
		
Если Найти(Источник, ".jpg") > 0 Тогда
	Соединение.setRequestHeader("Content-Type", "image/jpeg");
ИначеЕсли Найти(Источник, ".zip") > 0 Тогда
	Соединение.setRequestHeader("Content-Type", "application/zip");
ИначеЕсли Найти(Источник, ".xml") > 0 Тогда
	Соединение.setRequestHeader("Content-Type", "application/xml;charset=utf-8");
КонецЕсли;
	
Соединение.Send(Поток);
Поток.Close();
Показать
Оставьте свое сообщение

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