1 (изменено: MandarinKa02, 2017-07-17 00:14:01)

Тема: AHK: Работа с данными

Даже не знаю как тему назвать, но думаю суть понятна. "AHK: Работа с данными"

Начну с самого начала: есть сервер и клиент. Оба обмениваются текстом(без проблем). Радовался по началу когда достиг такого "успеха".(Для меня это уже успех(^_^) ) После, задумался как обмениваться не только текстом, но и файлами.. И вот тут настала тяжелая пора. Всё вроде хорошо отправляется, но есть одно большое НО.. Сервер и клиент пользуются протоколами TCP - то есть данные при отправки доходят с точностью 99%(у меня пока что данные не терялись)
Проблема  заключается в том что когда отправляешь какой-нибудь текст и через секунду данные(к примеру картинку) - то есть вероятность что оно придет склеенное(суть протокола TCP). К примеру:
Отправляю:

+ открыть спойлер

Hello World!
*101000101.... данные картинки*

Получаю:

+ открыть спойлер

Hello World!*101000101.... данные картинки*

Ответ должен прозвучать типо.. "Попробуй разделить одно от другого". А вопрос: Как это сделать?
Думаю объяснил по максимуму.
Ещё немного инфы:

+ открыть спойлер

Когда приходят данные, то вызывается функция
Peer(sAction, iSocket = 0, sName = 0, sAddr = 0, sPort = 0, ByRef bNewData = 0, bNewDataLength = 0)
{
...
}
и в ByRef bNewData = 0 сохраняются данные.

2

Re: AHK: Работа с данными

Имеет смысл покурить примеры из этой темы. Рассмотрены все популярные задачи при передаче данных, включая файлы.

Может кто более дословно поймёт, но на мой взгляд, очень расплывчато сформулирован вопрос, оставляя ощущение, что их скорее несколько.

По поводу - "Попробуй разделить одно от другого", при первом опыте возни с AHKsock, встречал упоминания на РУ-форумах, что после отправки очередного сообщения полезно вставлять "разделитель". Символ, или набор символов, натыкаясь на который, приёмник сообщения понимает, что предыдущее сообщение завершено. В него можно включать параметры, которые дополнительно могут как-то характеризовать тип следующего сообщения, будь то текст, или файл. Но у меня такой задачи не стояло, поэтому опытом поделиться не смогу. В любом случае, если в процессе получения данных ожидать заранее известные наборы разделителей, то проще и мух от котлет отделять и понимать, где, собственно мухи и где котлеты. Передаются ведь по сети в любом случае лишь нули и единицы, даже если это обычный текст.

3

Re: AHK: Работа с данными

KusochekDobra

Имеет смысл покурить примеры из этой темы. Рассмотрены все популярные задачи при передаче данных, включая файлы.

Именно это я использую. На сокетах работает скрипт. У меня в конце каждого пакета стоит разделитель, только вот как разделить данные? Я же не смогу при помощи RegExReplace() это всё разделить на две(а то и на три) части, правильно? RegEx работает с текстом, а не с "10001...".

4

Re: AHK: Работа с данными

Давайте вместе подумаем. Получать строку из её бинарного представления Вы умеете, следовательно, текстовые маркеры между сообщениями должны быть читаемы. Если это так, разделить строку на сообщения содержащиеся в ней - не проблема. Проблемой может стать понимание на стороне клиента, как обрабатывать сообщение, если оно НЕ текст. Значит, в маркере должен быть не только разделитель, но и указание на принадлежность следующего за ним двоичного кода, к какому-либо типу, или иной характеристике. Таким образом, вначале каждого сообщения можно разместить в таком же, текстовом виде тип сообщения и его расширение и обрабатывать их соответствующим образом.


msgSeparator	:= "<|"
paramSeparator	:= "ж"

incomingMSG		:= "<|text,msgжHello World!<|file,exeж1001011101101010...110111010110<|sound,mp3ж100000010100010011...0111011001"
allData := StrSplit(incomingMSG,msgSeparator)

Теперь, в массиве "allData" хранится каждое сообщение по отдельности. Получить и обработать каждое из них можно похожим образом:


Loop,% allData.Length() {
	msgData		:= StrSplit(allData[A_Index],paramSeparator)	; Отделить сообщение от параметров
	paramData	:= StrSplit(msgData[1],",")						; Разделить параметры
	ProcessMessage(msgData[2],paramData[1],paramData[2])		; Отправить в функцию на обработку
}

ProcessMessage(msg,type,ext) {
	if (type == "file") {
		if (ext == "exe") {
			; код обрабатывающий сообщение
		} else if (false) { ; другое расширение
			; код обрабатывающий сообщение
		}
	} else if (type == "sound") {
		if (ext == "mp3") {
			; код обрабатывающий сообщение
		} else if (false) { ; другое расширение
			; код обрабатывающий сообщение
		}
	} else if (type == "text") {
		if (ext == "msg") {
			; код обрабатывающий сообщение
		} else if (false) { ; другое расширение
			; код обрабатывающий сообщение
		}
	}
}

Вместо - "код обрабатывающий сообщение" - лучше сделать вызов функций, которые будут этим заниматься. Так же, в маркер можно помещать и длину сообщения. Это позволит отделять данные разных сообщений "налету". Ведь если известна длина сообщения, то заполненный в это значение лимит и будет означать его окончание.

5 (изменено: MandarinKa02, 2017-07-17 20:48:08)

Re: AHK: Работа с данными

KusochekDobra Не договорил насчет скрипта)
Строение пакета таково:

+ открыть спойлер

; Суть отправки
; #пакет, type, L, <тело сообщения>
;   type: 0 - ok (отправляет взамен "ok" при условии, что пакет был получен)
;   1 - text
;   2 - img
;   3 - file
;   4 - log
; Пример:
; "#5, 1, 12, привет"

То есть, #5 - номер отправляемого пакета, с каждой отправкой число увеличивается. Потом идет тип пакета, если какой-то текст то соответственно "text" и.т.д. L- длина тела сообщения. <тело сообщения> - Сами данные

У меня сейчас стоит скрипт на приёме, в котором есть условие:
If(StrLen(<тело сообщения>)*2 > L)
return -1

В кратце: если весит больше чем нужно, то return и потом отключаю его чтоб ошибок много не было.

6

Re: AHK: Работа с данными

Не обязательно выделять ник адресата сообщения в беседе из двух участников, как это не обязательно делать, если оно адресовано автору предыдущего поста. Следующим, стоит уточнить в ответе проблему, потому как на этом моменте я не понимаю сущность задачи, которую Вы перед собой поставили и главный её момент отобразить в названии темы этой беседы переименовав её как-то так -> "AHKsock. 'Суть проблемы'."

На вопрос из первого сообщения "Как это сделать?" - попытка ответить прозвучала.

7

Re: AHK: Работа с данными

Да, всё спасибо. Вопрос решен.