https запрос методом POST

1. ЧерныйКот 04.05.16 18:35 Сейчас в теме
Есть скрипт на php (запрос к API манго телеком). Нужно те же действия, что выполняет скрипт, сделать в 1С
<?php
$api_key = '62x9h7d4x29z23q71z0ypxv33j8heena';
$api_salt = 'nb4fg0evtell98utr9n6w9zqiyxmjbnw';
$url = 'https://app.mango-office.ru/vpbx/commands/callback';
$data = array(
 "command_id" => "your-command-id",
 "from" => array(
 "extension" => "313",
 "number" => ""
 ),
 "to_number" => "89536666669"
);

$json = json_encode($data);
$sign = hash('sha256', $api_key . $json . $api_salt);


$postdata = array(
 'vpbx_api_key' => $api_key,
 'sign' => $sign,
 'json' => $json
);

$post = http_build_query($postdata);

$opts = array(
 'http' => array(
 'method' => 'POST',
 'header' => 'Content-type: application/x-www-form-urlencoded',
 'content' => $post
 )
);
$context = stream_context_create($opts);
$response = file_get_contents($url, false, $context);

?>

Показать

$postdata, $post - проблем нет. всё символ в символ также.
$opts, $context - как правильно рассчитать и передать в 1С в тело запроса ????

код 1С:
	СертификатОС = Новый СертификатКлиентаWindows();
	ЗащищенноеСоединение = Новый ЗащищенноеСоединениеOpenSSL(СертификатОС);
	АдресДляСоединения = СтрЗаменить(Объект.МангоАдрес, "https://", "");
	Соединение = Новый HTTPСоединение(АдресДляСоединения,,,,,, ЗащищенноеСоединение);
	
	//{ JSON
// расчет sign, СтрокаJson
	//} JSON
	
	
	postdata = Новый Соответствие;
	postdata.Вставить("vpbx_api_key", Объект.МангоКод);
	postdata.Вставить("sign", sign);
	postdata.Вставить("json", СтрокаJson);
	
	post = "vpbx_api_key=" + postdata.Получить("vpbx_api_key")  +"&"+ 
	"sign=" + postdata.Получить("sign")			    +"&"+  
	"json=" + postdata.Получить("json");
	
		Параметрыhttp = Новый Соответствие;
	Параметрыhttp.Вставить("method", "POST");
	Параметрыhttp.Вставить("header", "Content-type: application/x-www-form-urlencoded");
	Параметрыhttp.Вставить("content", post);
	
	opts = Новый Соответствие;
	opts.Вставить("http", Параметрыhttp);

	АдресЗапроса = "/vpbx/commands/callback";
	//
	//ЗаголовкиЗапроса = Новый Соответствие;
	//ЗаголовкиЗапроса.Вставить("Content-Type","multipart/form-data; boundary=My1cV8bNdr");
	
	ЗапросАПИ = Новый HTTPЗапрос(АдресЗапроса);
	ЗапросАПИ.УстановитьТелоИзСтроки(post);
	
	ОтветАПИ = Соединение.ОтправитьДляОбработки(ЗапросАПИ);
Показать

на выходе ошибка 401: не авторизованы
По теме из базы знаний
Ответы
Подписаться на ответы Инфостарт бот Сортировка: Древо развёрнутое
Свернуть все
6. PetroP 05.05.16 13:15 Сейчас в теме
(1) ЧерныйКот, не дождавшись помощи тру-пхпшников, я поступал следующим образом. Запускал скрипт на веб-сервере, ловил запрос фидлером, смотрел результат и реализовывал в 1с.
ЧерныйКот; +1 Ответить
30. bestuzhev 684 23.11.17 12:34 Сейчас в теме
(1) Проблема вся в заголовках, как только ты начинаешь передавать нормальные заголовки- все начинает работать.
1) у тебя идет
  
Параметрыhttp = Новый Соответствие;
    Параметрыhttp.Вставить("method", "POST");
    Параметрыhttp.Вставить("header", "Content-type: application/x-www-form-urlencoded");
    Параметрыhttp.Вставить("content", post);


но при этом ты нигде дальше это не используешь, я заменил на

    
Параметрыhttp = Новый Соответствие;
    Параметрыhttp.Вставить("Accept-Language", "ru");
    Параметрыhttp.Вставить("Accept-Charset", "utf-8");
    Параметрыhttp.Вставить("Content-Language", "ru");
    Параметрыhttp.Вставить("Content-Charset", "utf-8");
    Параметрыhttp.Вставить("Content-type", "application/x-www-form-urlencoded; charset=utf-8");


и
    ЗапросАПИ = Новый HTTPЗапрос(АдресЗапроса,Параметрыhttp);


Все заработало!
2. dj_serega 394 04.05.16 20:45 Сейчас в теме
а почему нет юзера и пароля в Новый HTTPСоединение ?
3. ЧерныйКот 04.05.16 22:29 Сейчас в теме
(2) dj_serega, там авторизация не прямая, сервер принимает все запросы, а авторизация на каждый запрос отдельно - через параметры vpbx_api_key и sign
Ошибка тут 100% : ЗапросАПИ.УстановитьТелоИзСтроки(post); т.е. неверно формируется тело запроса, а вот как сделать такое же тело запроса как в php скрипте - я не знаю...
4. dj_serega 394 05.05.16 07:11 Сейчас в теме
(3) ЧерныйКот, А попробуйте еще так:
post = "?vpbx_api_key="
ЧерныйКот; +1 Ответить
5. ЧерныйКот 05.05.16 11:34 Сейчас в теме
(4) dj_serega, увы не помогло
7. ЧерныйКот 05.05.16 17:48 Сейчас в теме
Решил проблему. Но не методами 1С...
WinHttp = Новый COMОбъект("WinHttp.WinHttpRequest.5.1"); всё отработало отлично.
Аналогичный POST запрос из 1С - не отрабатывал, причину так и не выяснил (((

Всем спасибо за помощь. Если кто знает причину проблемы в 1С - напишите пожалуйста.
10. Nost_ 09.08.16 14:50 Сейчас в теме
(7) ЧерныйКот, можешь кинуть пример рабочего кода с WinHttp?!
14. herfis 516 09.08.16 17:07 Сейчас в теме
(7) ЧерныйКот, Попробуй
Соединение = Новый HTTPСоединение(Сервер,Порт,,,,, Новый ЗащищенноеСоединениеOpenSSL(Неопределено, Неопределено));

для неавторизованного https-соединения. Может, дело и не в установке тела сообщения...
Чтобы гарантированно понять, в чем дело, надо сравнить реальные оправляемые данные... Но для этого придется отладочный веб-сервер поднимать.
ЧерныйКот; +1 Ответить
15. ЧерныйКот 09.08.16 17:16 Сейчас в теме
(14) herfis, пробовал все варианты.
дело не в авторизации. мне прислали тексты запросов которые уходят с моей стороны. Так там тело запроса, который был создан методами 1С - просто содержало другие данные (точнее другую структуру данных), чем тот же запрос (символ в символ) , но отправленный WinHttp.
16. SeverBaP 5 09.08.16 17:18 Сейчас в теме
(15) ЧерныйКот, приведи пример тех текстов
8. po-1c 1 18.05.16 12:54 Сейчас в теме
Запрос страниц через объект HTTPСоединение подробно описывается здесь
http://1clenta.ru/pattern/29
9. Nost_ 09.08.16 14:47 Сейчас в теме
ЧерныйКот, можешь кинуть пример рабочего кода с WinHttp?!
11. ЧерныйКот 09.08.16 15:36 Сейчас в теме
типа того:
	СтрокаJson = "{}";
	
	Хеширование = Новый ХешированиеДанных(ХешФункция.SHA256);
	Хеширование.Добавить(Объект.МангоКод); // vpbx_api_key
	Хеширование.Добавить(СтрокаJson);      // json
	Хеширование.Добавить(Объект.МангоКлюч);// vpbx_api_salt
	sign = Хеширование.ХешСумма;
	sign = СтрЗаменить(НРЕГ(sign), " ", "");
	
	postdata = Новый Соответствие;
	postdata.Вставить("vpbx_api_key", Объект.МангоКод);
	postdata.Вставить("sign", sign);
	postdata.Вставить("json", СтрокаJson);
	
	post = "vpbx_api_key=" + postdata.Получить("vpbx_api_key")  + "&" +
	"sign=" + postdata.Получить("sign")							+ "&" +
	"json=" + postdata.Получить("json");
	
	Попытка
		WinHttp = Новый COMОбъект("WinHttp.WinHttpRequest.5.1");
		WinHttp.Option(2,"utf-8");
		WinHttp.Open("POST",Объект.МангоАдрес+"config/users/request",0);
		WinHttp.SetRequestHeader("Accept-Language", "ru");
		WinHttp.SetRequestHeader("Accept-Charset","utf-8");
		WinHttp.setRequestHeader("Content-Language", "ru");
		WinHttp.setRequestHeader("Content-Charset", "utf-8");
		WinHttp.setRequestHeader("Content-type", "application/x-www-form-urlencoded; charset=utf-8");
		ТелоПОСТ = post;
		WinHttp.Send(ТелоПОСТ);
		ТекстОтвета = WinHttp.ResponseText();
	Исключение
		ТекстПредупреждения = ОписаниеОшибки();
	КонецПопытки;	
	
	Если WinHttp.Status <> 200 Тогда
		ТекстПредупреждения = Строка(WinHttp.Status) + Символы.ПС + ТекстПредупреждения;
	КонецЕсли;

Показать
12. SeverBaP 5 09.08.16 16:52 Сейчас в теме
	vpbx_api_key = "";
	vpbx_api_salt = "";
	
	СтрокаJson="{}";

	Хеширование = Новый ХешированиеДанных(ХешФункция.SHA256);
    Хеширование.Добавить(vpbx_api_key);
    Хеширование.Добавить(СтрокаJson);
    Хеширование.Добавить(vpbx_api_salt);
	
    sign = Хеширование.ХешСумма;
    sign = СтрЗаменить(НРЕГ(sign), " ", "");
	
	СерверПриемник = "app.mango-office.ru";
	
	HTTPСоединение = Новый HTTPСоединение(СерверПриемник,,,,Новый ИнтернетПрокси,,Новый ЗащищенноеСоединениеOpenSSL(Новый СертификатКлиентаWindows));
	
	ЗаголовкиHTTP = Новый Соответствие;
	ЗаголовкиHTTP.Вставить("Connection", "keep-alive");
	ЗаголовкиHTTP.Вставить("Content-Type","application/x-www-form-urlencoded");
	
	АдресСтраницыНаСервере = "vpbx/config/users/request";
	СтрокаНаОтправку = "vpbx_api_key = "+vpbx_api_key+"
 	|sign = "+sign+"
 	|json = "+СтрокаJson;
	
	
	//Формируем HTTP запрос
	ЗапросHTTP = Новый HTTPЗапрос(АдресСтраницыНаСервере, ЗаголовкиHTTP);
	ЗапросHTTP.УстановитьТелоИзСтроки(СтрокаНаОтправку);

	ОтветHTTP = Неопределено;

	Попытка
		
		//Ответ от сервера получим в возвращаемом значении типа HTTPОтвет
		ОтветHTTP = HTTPСоединение.Получить(ЗапросHTTP);
		Сообщить(ОтветHTTP.ПолучитьТелоКакСтроку());
	Исключение
		
		Сообщить(ОписаниеОшибки());		
		
	КонецПопытки;
Показать

Попробуй что выдаст
18. ЧерныйКот 09.08.16 17:38 Сейчас в теме
(12) SeverBaP, с символами переноса в теле запроса тоже пробовал. и возврат каретки тоже, и через Символ(Код)
а вот код в (11) - полностью рабочий. с тем же телом запроса.
19. PetroP 09.08.16 17:56 Сейчас в теме
(18) ЧерныйКот, народ просто не смотрит дату обсуждения, и не понимает, что вопрос уже решен...
20. ЧерныйКот 09.08.16 17:58 Сейчас в теме
(19) PetroP, но интересно же почему методами 1С ничего не получилось.
22. PetroP 10.08.16 09:13 Сейчас в теме
(20) ЧерныйКот, опять же, надо видеть raw-текст правильного запроса.
23. herfis 516 10.08.16 09:29 Сейчас в теме
(22) PetroP, Народ просто не читает ветку и не видит, что raw-тексты правильного и неправильного запроса уже выкладывались.
24. SeverBaP 5 10.08.16 10:14 Сейчас в теме
(23) herfis, дело в том что я видел реализацию через COM-объект который сейчас в рабочий в этой теме. Но хочется реализовать через штатные механизмы 1С. У меня по обмену данными через разные API опыт есть - из этого могу с уверенностью сказать что доступные средства 1с НЕ ВСЕГДА позволяют это красиво сделать без участия этого COM объекта (ведь иногда клиенты и не на "Винде"). Но все же иногда и получается после долгих мучений и поиска ошибок можно это сделать. Почему же я на этой теме завис - потому что я хочу найти решение 1С-ое без компонент и для общего развития так как интересно.
25. ЧерныйКот 10.08.16 10:18 Сейчас в теме
(24) SeverBaP,
потому что я хочу найти решение 1С-ое без компонент и для общего развития так как интересно.

+++ тоже интересно
26. PetroP 10.08.16 12:06 Сейчас в теме
(23) herfis, должен заметить, что именно raw-текстов здесь нет. Обрывки джейсона не есть raw-текстом.
21. herfis 516 09.08.16 18:06 Сейчас в теме
(18) ЧерныйКот, Интересно, спасибо.
(19) PetroP, Народ видит, что автор на связи, а вопрос что было не так с нативным способом - оставался.
13. Serginio 943 09.08.16 17:03 Сейчас в теме
Берешь в руки фиддлер и сравниваешь запросы
17. ЧерныйКот 09.08.16 17:36 Сейчас в теме
Цитирую:
Андрей, от Вас приходит такой запрос(см. скриншот ниже)

Поля сигн и апикей - верные. Но приходит в одну строчку всё

...
"MSG": "Received request",
"IP": "**.**.***.***",
"PARAMETERS": {
   "USER_AGENT": "1C+Enterprise/8.3",
   "REQUEST_URI": "/vpbx/vpbx/config/users/request&vpbx_api_key=*****&json=*****&sign=*****"
},
...
Вот снизу пример правильный, как должно приходить:
...
"PARAMETERS": {
   "REQUEST_URI": "/vpbx/vpbx/config/users/request",
   "POST": {
       "vpbx_api_key": "*****",
       "json": "*****",
       "sign": "*****" 
   }
},
...
Показать
27. PetroP 10.08.16 12:09 Сейчас в теме
Если все удалось построить на "WinHttp.WinHttpRequest", то нет ничего сложного запустить тот же Fiddler, прочитать запрос и показать (предварительно заменив конфиденциальную информацию).
28. ЧерныйКот 10.08.16 12:17 Сейчас в теме
(27) PetroP, будет время - обязательно попробую покопаться.
29. Serginio 943 10.08.16 13:19 Сейчас в теме
Вобще у 1С много ошибок от версии к версии. Попрбуй на новой версии
http://www.forum.mista.ru/topic.php?id=776480
31. svilsa 13 02.04.19 21:45 Сейчас в теме
Параметры = Новый Соответствие;
	Параметры.Вставить("Content-Type", "application/x-www-form-urlencoded");
	HTTPЗапрос = Новый HTTPЗапрос(АдресЗапроса, Параметры);
 


Мне помогло добавление параметра "Content-Type", "application/x-www-form-urlencoded". Без него, в запрос Post не получалось передать параметр
32. user2129412 24.02.25 19:02 Сейчас в теме
Добрый день!
Есть небольшие неточности, например в заголовках. Вот рабочий пример по отправки post запроса на создание issues на gitlab, там отличие в том что тело запроса отправляется в виде json.

&НаКлиенте
Процедура Отправить(Команда)
	СертификатОС = Новый СертификатКлиентаWindows();
    ЗащищенноеСоединение = Новый ЗащищенноеСоединениеOpenSSL(СертификатОС);
    АдресДляСоединения = "gitlab.com";
    Соединение = Новый HTTPСоединение(АдресДляСоединения,,,,,, ЗащищенноеСоединение);
	
	//Данные задачи (issues)
    postJSON = Новый Структура;
	postJSON.Вставить("title", "Наименование");
	postJSON.Вставить("description", "Описание");
	postJSON.Вставить("labels", "Метки");
	
	//Запись json для тела запроса
	ЗаписьJSON = Новый ЗаписьJSON;			
	ЗаписьJSON.УстановитьСтроку();
	ЗаписатьJSON(ЗаписьJSON,postJSON);			
	jsonStr = ЗаписьJSON.Закрыть();  
	
	
	//Заголовки http с токеном
    Заголовкиhttp = Новый Соответствие;
    Заголовкиhttp.Вставить("method", "POST");
    Заголовкиhttp.Вставить("Content-type", "application/json");
	Заголовкиhttp.Вставить("Private-Token", "ваш токен для доступа к проекту");
    
    АдресЗапроса = "/api/v4/projects/project_id/issues";     //project_id - id проекта на gitlab
    
    ЗапросАПИ = Новый HTTPЗапрос(АдресЗапроса);   
	ЗапросАПИ.Заголовки = Заголовкиhttp;
    ЗапросАПИ.УстановитьТелоИзСтроки(jsonStr);
    
    ОтветАПИ = Соединение.ОтправитьДляОбработки(ЗапросАПИ);    
	стрОтвет = ОтветАПИ.ПолучитьТелоКакСтроку();
	Сообщить(стрОтвет);
КонецПроцедуры
Показать
Оставьте свое сообщение

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