Exemple #1
0
void CSteamProto::OnGotHistoryMessages(const HttpResponse *response, void *arg)
{
	MCONTACT hContact = FindContact((char*)arg);
	if (!hContact)
		return;

	if (!ResponseHttpOk(response))
		return;

	JSONROOT root(response->pData);
	if (root == NULL)
		return;

	JSONNode *node = json_get(root, "response");

	JSONNode *messages = json_get(node, "messages");
	JSONNode *nmessages = json_as_array(messages);

	// Self SteamID
	ptrA steamId(getStringA("SteamID"));

	for (size_t i = json_size(nmessages); i > 0; i--)
	{
		JSONNode *message = json_at(nmessages, i - 1);

		node = json_get(message, "accountid");
		const char *authorSteamId = AccountIdToSteamId(_ttoi64(ptrT(json_as_string(node))));

		node = json_get(message, "message");
		ptrT text(json_as_string(node));
		T2Utf szMessage(text);

		node = json_get(message, "timestamp");
		time_t timestamp = _ttoi64(ptrT(json_as_string(node)));

		// Ignore already existing messages
		if (timestamp <= m_lastMessageTS)
			continue;

		PROTORECVEVENT recv = { 0 };
		recv.timestamp = timestamp;
		recv.szMessage = szMessage;

		if (strcmp(steamId, authorSteamId))
		{
			// Received message
			ProtoChainRecvMsg(hContact, &recv);
		}
		else
		{
			// Sent message
			recv.flags = PREF_SENT;
			Proto_RecvMessage(hContact, &recv);
		}
	}

	json_delete(nmessages);
}
Exemple #2
0
void CIcqProto::handleXtrazData(DWORD dwUin, DWORD dwMID, DWORD dwMID2, WORD wCookie, char* szMsg, int nMsgLen, BOOL bThruDC)
{
	MCONTACT hContact;
	char* szPluginID;

	hContact = HContactFromUIN(dwUin, NULL);
	if (hContact) // user sent us xtraz, he supports it
		SetContactCapabilities(hContact, CAPF_XTRAZ);

	szPluginID = getXmlPidItem(szMsg, nMsgLen);
	if (!strcmpnull(szPluginID, "viewCard")) { // it is a greeting card
		char *szWork, *szEnd, *szUrl, *szNum;

		szWork = strstrnull(szMsg, "<InD>");
		szEnd = strstrnull(szMsg, "</InD>");
		if (szWork && szEnd) {
			int nDataLen = szEnd - szWork;

			szUrl = (char*)_alloca(nDataLen);
			memcpy(szUrl, szWork + 5, nDataLen);
			szUrl[nDataLen - 5] = '\0';

			if (!_strnicmp(szUrl, "view_", 5)) {
				szNum = szUrl + 5;
				szWork = strstrnull(szUrl, ".html");
				if (szWork) {
					strcpy(szWork, ".php");
					strcat(szWork, szWork + 5);
				}
				while (szWork = strstrnull(szUrl, "&amp;"))  // unescape &amp; code
					strcpy(szWork + 1, szWork + 5);

				szWork = (char*)SAFE_MALLOC(nDataLen + MAX_PATH);
				ICQTranslateUtfStatic(LPGEN("Greeting card:"), szWork, MAX_PATH);
				strcat(szWork, "\r\nhttp://www.icq.com/friendship/pages/view_page_");
				strcat(szWork, szNum);

				// Create message to notify user
				PROTORECVEVENT pre = { 0 };
				pre.timestamp = time(NULL);
				pre.szMessage = szWork;
				pre.flags = PREF_UTF;

				int bAdded;
				ProtoChainRecvMsg(HContactFromUIN(dwUin, &bAdded), &pre);

				SAFE_FREE(&szWork);
			}
			else NetLog_Uni(bThruDC, "Error: Non-standard greeting card message");
		}
		else NetLog_Uni(bThruDC, "Error: Malformed greeting card message");
	}
	else NetLog_Uni(bThruDC, "Error: Unknown plugin \"%s\" in Xtraz message", szPluginID);

	SAFE_FREE(&szPluginID);
}
Exemple #3
0
void ShowMessageInlineUtf(const MCONTACT hContact, const char *msg) {
	char buff[1024];
	mir_snprintf(buff, 1024, "%s%s", Translate(LANG_INLINE_PREFIX), msg);

	PROTORECVEVENT pre = {0};
	pre.timestamp = time(0);
	pre.szMessage = buff;
	pre.flags = PREF_UTF|PREF_BYPASS_OTR;
	ProtoChainRecvMsg(hContact, &pre);
}
Exemple #4
0
void ShowMessageInline(const MCONTACT hContact, const wchar_t *msg) {
	wchar_t buff[1024];
	mir_snwprintf(buff, L"%s%s", _A2W(LANG_INLINE_PREFIX), msg);
	T2Utf utf(buff);

	PROTORECVEVENT pre = {0};
	pre.timestamp = time(0);
	pre.szMessage = utf;
	pre.flags = PREF_BYPASS_OTR;
	ProtoChainRecvMsg(hContact, &pre);	
}
Exemple #5
0
void ShowMessageInline(const MCONTACT hContact, const TCHAR *msg) {
	TCHAR buff[1024];
	mir_sntprintf(buff, 1024, _T("%s%s"), TranslateT(LANG_INLINE_PREFIX), msg);

	PROTORECVEVENT pre = {0};
	pre.timestamp = time(0);
	char *utf = mir_utf8encodeT(buff);
	pre.szMessage = utf;
	pre.flags = PREF_UTF|PREF_BYPASS_OTR;
	ProtoChainRecvMsg(hContact, &pre);	

	mir_free(utf);
}
Exemple #6
0
void CVkProto::AddFeedEvent(CMString& tszBody, time_t tTime)
{
	if (tszBody.IsEmpty()) {
		debugLogA("CVkProto::AddFeedEvent %d", tTime);
		return;
	}
	
	MCONTACT hContact = FindUser(VK_FEED_USER, true);
	T2Utf pszBody(tszBody);

	PROTORECVEVENT recv = { 0 };
	recv.timestamp = tTime;
	recv.szMessage = pszBody;
	recv.lParam = 0;
	recv.pCustomData = NULL;
	recv.cbCustomDataSize = 0;
	ProtoChainRecvMsg(hContact, &recv);
}
Exemple #7
0
void TwitterProto::UpdateMessages(bool pre_read)
{
	try
	{
		ScopedLock s(twitter_lock_);
		twitter::status_list messages = twit_.get_direct(dm_since_id_);
		s.Unlock();

		if(messages.size())
			dm_since_id_ = std::max(dm_since_id_, messages[0].status.id);

		for(twitter::status_list::reverse_iterator i=messages.rbegin(); i!=messages.rend(); ++i)
		{
			HANDLE hContact = AddToClientList(i->username.c_str(),"");

			PROTORECVEVENT recv = { 0 };
			recv.flags = PREF_UTF;
			if(pre_read)
				recv.flags |= PREF_CREATEREAD;
			recv.szMessage = const_cast<char*>(i->status.text.c_str());
			recv.timestamp = static_cast<DWORD>(i->status.time);
			ProtoChainRecvMsg(hContact, &recv);
		}

		db_pod_set(0,m_szModuleName,TWITTER_KEY_DMSINCEID,dm_since_id_);
		disconnectionCount = 0;
		debugLogA( _T("***** Direct messages updated"));
	}
	catch(const bad_response &)
	{
		++disconnectionCount;
		debugLogA( _T("***** UpdateMessages - Bad response from server, this has happened %d time(s)"), disconnectionCount);
		if (disconnectionCount > 2) {
			debugLogA( _T("***** UpdateMessages - Too many bad responses from the server, signing off"));
			SetStatus(ID_STATUS_OFFLINE);
		}
	}
	catch(const std::exception &e)
	{
		ShowPopup( (std::string("While updating direct messages, an error occurred: ")+e.what()).c_str());
		debugLogA( _T("***** Error updating direct messages: %s"), e.what());
	}
}
Exemple #8
0
void CVkProto::AddFeedEvent(CVKNewsItem& vkNewsItem)
{
    if (vkNewsItem.tszText.IsEmpty())
        return;

    MCONTACT hContact = FindUser(VK_FEED_USER, true);
    T2Utf pszBody(vkNewsItem.tszText);

    PROTORECVEVENT recv = { 0 };
    recv.timestamp = vkNewsItem.tDate;
    recv.szMessage = pszBody;
    recv.lParam = 0;
    recv.pCustomData = NULL;
    recv.cbCustomDataSize = 0;

    if (m_bUseNonStandardNotifications) {
        recv.flags = PREF_CREATEREAD;
        MsgPopup(hContact, vkNewsItem.tszPopupText, vkNewsItem.tszPopupTitle);
    }

    ProtoChainRecvMsg(hContact, &recv);
}
void CSteamProto::ParsePollData(JSONNode *data)
{
	JSONNode *node, *item = NULL;

	std::string steamIds;
	for (size_t i = 0; i < json_size(data); i++)
	{
		item = json_at(data, i);
		if (item == NULL)
			break;

		node = json_get(item, "steamid_from");
		ptrA steamId(mir_t2a(ptrT(json_as_string(node))));

		node = json_get(item, "utc_timestamp");
		time_t timestamp = atol(ptrA(mir_t2a(ptrT(json_as_string(node)))));

		node = json_get(item, "type");
		ptrT type(json_as_string(node));
		if (!lstrcmpi(type, _T("saytext")) || !lstrcmpi(type, _T("emote")) ||
			!lstrcmpi(type, _T("my_saytext")) || !lstrcmpi(type, _T("my_emote")))
		{
			MCONTACT hContact = FindContact(steamId);
			if (!hContact)
				continue;

			node = json_get(item, "text");
			ptrT text(json_as_string(node));
			T2Utf szMessage(text);

			if (_tcsstr(type, _T("my_")) == NULL)
			{
				PROTORECVEVENT recv = { 0 };
				recv.timestamp = timestamp;
				recv.szMessage = szMessage;
				ProtoChainRecvMsg(hContact, &recv);
			}
			else
			{
				AddDBEvent(hContact, EVENTTYPE_MESSAGE, timestamp, DBEF_UTF | DBEF_SENT, (int)mir_strlen(szMessage) + 1, (PBYTE)(char*)szMessage);
			}
		}
		else if (!lstrcmpi(type, _T("typing")))
		{
			MCONTACT hContact = FindContact(steamId);
			if (hContact)
			{
				CallService(MS_PROTO_CONTACTISTYPING, hContact, (LPARAM)STEAM_TYPING_TIME);
			}
		}
		else if (!lstrcmpi(type, _T("personastate")))
		{
			node = json_get(item, "persona_state");
			int status = node ? SteamToMirandaStatus(json_as_int(node)) : -1;

			if (IsMe(steamId))
			{
				node = json_get(item, "persona_name");
				setTString("Nick", ptrT(json_as_string(node)));

				if (status == -1 || status == ID_STATUS_OFFLINE)
					continue;

				if (status != m_iStatus)
				{
					debugLog(_T("CSteamProto::ParsePollData: Change own status to %i"), status);
					int oldStatus = m_iStatus;
					m_iStatus = m_iDesiredStatus = status;
					ProtoBroadcastAck(NULL, ACKTYPE_STATUS, ACKRESULT_SUCCESS, (HANDLE)oldStatus, m_iStatus);
				}

				continue;
			}
			
			MCONTACT hContact = FindContact(steamId);
			if (hContact == NULL)
				continue; // probably this is info about random player playing on same server, so we ignore it

			if (status != -1)
				SetContactStatus(hContact, status);

			node = json_get(item, "persona_name");
			setTString(hContact, "Nick", ptrT(json_as_string(node)));

			// todo: find difference between state changing and info changing
			steamIds.append(steamId).append(",");
		}
		else if (!lstrcmpi(type, _T("personarelationship")))
		{
			node = json_get(item, "persona_state");
			int state = json_as_int(node);

			switch (state)
			{
			case 0:
				{// removed
					MCONTACT hContact = FindContact(steamId);
					if (hContact)
					{
						ContactIsRemoved(hContact);
					}
				}
				break;

			case 1:
				{// ignored
					MCONTACT hContact = FindContact(steamId);
					if (hContact)
					{
						ContactIsIgnored(hContact);
					}
				}
				break;

			case 2:
				{// auth request
					/*MCONTACT hContact = FindContact(steamId);
					if (!hContact)
						hContact = AddContact(steamId, true);*/

					//RaiseAuthRequestThread((void*)hContact);

					ptrA token(getStringA("TokenSecret"));

					PushRequest(
						new GetUserSummariesRequest(token, steamId),
						&CSteamProto::OnAuthRequested,
						mir_strdup(steamId),
						MirFreeArg);
				}
				break;

			case 3:
				// add to list
				// todo
				break;

			default: continue;
			}
		}
		/*else if (!lstrcmpi(type, _T("leftconversation")))
		{
		}*/
		else
		{
			continue;
		}
	}

	if (!steamIds.empty())
	{
		steamIds.pop_back();
		ptrA token(getStringA("TokenSecret"));

		PushRequest(
			new GetUserSummariesRequest(token, steamIds.c_str()),
			&CSteamProto::OnGotUserSummaries);
	}
}
Exemple #10
0
void CVkProto::OnReceiveMessages(NETLIBHTTPREQUEST *reply, AsyncHttpRequest *pReq)
{
	debugLogA("CVkProto::OnReceiveMessages %d", reply->resultCode);
	if (reply->resultCode != 200)
		return;

	JSONNode jnRoot;
	const JSONNode &jnResponse = CheckJsonResponse(pReq, reply, jnRoot);
	if (!jnResponse)
		return;
	if (!jnResponse["Msgs"])
		return;

	CMStringA mids;
	int numMessages = jnResponse["Msgs"]["count"].as_int();
	const JSONNode &jnMsgs = jnResponse["Msgs"]["items"];
	const JSONNode &jnFUsers = jnResponse["fwd_users"];

	debugLogA("CVkProto::OnReceiveMessages numMessages = %d", numMessages);

	for (auto it = jnMsgs.begin(); it != jnMsgs.end(); ++it) {
		const JSONNode &jnMsg = (*it);
		if (!jnMsg) {
			debugLogA("CVkProto::OnReceiveMessages pMsg == NULL");
			break;
		}

		UINT mid = jnMsg["id"].as_int();
		CMString tszBody(jnMsg["body"].as_mstring());
		int datetime = jnMsg["date"].as_int();
		int isOut = jnMsg["out"].as_int();
		int isRead = jnMsg["read_state"].as_int();
		int uid = jnMsg["user_id"].as_int();

		const JSONNode &jnFwdMessages = jnMsg["fwd_messages"];
		if (jnFwdMessages) {
			CMString tszFwdMessages = GetFwdMessages(jnFwdMessages, jnFUsers, m_vkOptions.BBCForAttachments());
			if (!tszBody.IsEmpty())
				tszFwdMessages = _T("\n") + tszFwdMessages;
			tszBody +=  tszFwdMessages;
		}

		CMString tszAttachmentDescr;
		const JSONNode &jnAttachments = jnMsg["attachments"];
		if (jnAttachments) {
			tszAttachmentDescr = GetAttachmentDescr(jnAttachments, m_vkOptions.BBCForAttachments());
			if (!tszBody.IsEmpty())
				tszBody += _T("\n");
			tszBody += tszAttachmentDescr;
		}

		MCONTACT hContact = NULL;
		int chat_id = jnMsg["chat_id"].as_int();
		if (chat_id == 0)
			hContact = FindUser(uid, true);

		char szMid[40];
		_itoa(mid, szMid, 10);
		if (m_vkOptions.iMarkMessageReadOn == MarkMsgReadOn::markOnReceive || chat_id != 0) {
			if (!mids.IsEmpty())
				mids.AppendChar(',');
			mids.Append(szMid);
		}

		if (chat_id != 0) {
			debugLogA("CVkProto::OnReceiveMessages chat_id != 0");
			CMString action_chat = jnMsg["action"].as_mstring();
			int action_mid = _ttoi(jnMsg["action_mid"].as_mstring());
			if ((action_chat == "chat_kick_user") && (action_mid == m_myUserId))
				KickFromChat(chat_id, uid, jnMsg, jnFUsers);
			else {
				MCONTACT chatContact = FindChat(chat_id);
				if (chatContact && getBool(chatContact, "kicked", true))
					db_unset(chatContact, m_szModuleName, "kicked");
				AppendChatMessage(chat_id, jnMsg, jnFUsers, false);
			}
			continue;
		}

		PROTORECVEVENT recv = { 0 };
		bool bUseServerReadFlag = m_vkOptions.bSyncReadMessageStatusFromServer ? true : !m_vkOptions.bMesAsUnread;
		if (isRead && bUseServerReadFlag)
			recv.flags |= PREF_CREATEREAD;
		if (isOut)
			recv.flags |= PREF_SENT;
		else if (m_vkOptions.bUserForceInvisibleOnActivity && time(NULL) - datetime < 60 * m_vkOptions.iInvisibleInterval)
			SetInvisible(hContact);

		T2Utf pszBody(tszBody);
		recv.timestamp = m_vkOptions.bUseLocalTime ? time(NULL) : datetime;
		recv.szMessage = pszBody;
		recv.lParam = isOut;
		recv.pCustomData = szMid;
		recv.cbCustomDataSize = (int)mir_strlen(szMid);
		Sleep(100);

		debugLogA("CVkProto::OnReceiveMessages mid = %d, datetime = %d, isOut = %d, isRead = %d, uid = %d", mid, datetime, isOut, isRead, uid);

		if (!CheckMid(m_sendIds, mid)) {
			debugLogA("CVkProto::OnReceiveMessages ProtoChainRecvMsg");
			ProtoChainRecvMsg(hContact, &recv);
			if (mid > getDword(hContact, "lastmsgid", -1))
				setDword(hContact, "lastmsgid", mid);
			if (!isOut)
				m_incIds.insert((HANDLE)mid);
		}
		else if (m_vkOptions.bLoadSentAttachments && !tszAttachmentDescr.IsEmpty() && isOut) {
			T2Utf pszAttach(tszAttachmentDescr);
			recv.timestamp = time(NULL); // only local time
			recv.szMessage = pszAttach;
			ProtoChainRecvMsg(hContact, &recv);
		}
	}

	if (!mids.IsEmpty())
		MarkMessagesRead(mids);
}
Exemple #11
0
void CVkProto::OnReceiveMessages(NETLIBHTTPREQUEST *reply, AsyncHttpRequest *pReq)
{
	debugLogA("CVkProto::OnReceiveMessages %d", reply->resultCode);
	if (reply->resultCode != 200)
		return;

	JSONROOT pRoot;
	JSONNODE *pResponse = CheckJsonResponse(pReq, reply, pRoot);
	if (pResponse == NULL)
		return;

	JSONNODE *pDlgs = json_as_array(json_get(pResponse, "dlgs"));
	if (pDlgs != NULL) {
		int numDialogs = json_as_int(json_at(pDlgs, 0));
		for (int i = 1; i <= numDialogs; i++) {
			JSONNODE *pDlg = json_at(pDlgs, i);
			if (pDlg == NULL)
				continue;

			int chatid = json_as_int(json_get(pDlg, "chat_id"));
			if (chatid != 0)
			if (m_chats.find((CVkChatInfo*)&chatid) == NULL) {
				AppendChat(chatid, pDlg);
			}
		}
	}

	CMStringA mids, lmids;
	bool bDirectArray = false;

	JSONNODE *pMsgs = json_as_array(json_get(pResponse, "msgs"));
	if (pMsgs == NULL) {
		pMsgs = pResponse;
		bDirectArray = true;
	}

	int numMessages = json_as_int(json_at(pMsgs, 0));
	for (int i = 1; i <= numMessages; i++) {
		JSONNODE *pMsg = json_at(pMsgs, i);
		if (pMsg == NULL)
			continue;

		char szMid[40];
		int mid = json_as_int(json_get(pMsg, "mid"));
		_itoa(mid, szMid, 10);
		if (!mids.IsEmpty())
			mids.AppendChar(',');
		mids.Append(szMid);

		int chat_id = json_as_int(json_get(pMsg, "chat_id"));
		if (chat_id != 0) {
			AppendChatMessage(chat_id, pMsg, false);
			continue;
		}

		// VK documentation lies: even if you specified preview_length=0, 
		// long messages get cut out. So we need to retrieve them from scratch
		ptrT ptszBody(json_as_string(json_get(pMsg, "body")));
		if (!bDirectArray && _tcslen(ptszBody) > 1000) {
			if (!lmids.IsEmpty())
				lmids.AppendChar(',');
			lmids.Append(szMid);
			continue;
		}

		int datetime = json_as_int(json_get(pMsg, "date"));
		int isOut = json_as_int(json_get(pMsg, "out"));
		int uid = json_as_int(json_get(pMsg, "uid"));
		int isRead = json_as_int(json_get(pMsg, "read_state"));

		JSONNODE *pAttachments = json_get(pMsg, "attachments");
		if (pAttachments != NULL)
			ptszBody = mir_tstrdup(CMString(ptszBody) + GetAttachmentDescr(pAttachments));

		MCONTACT hContact = FindUser(uid, true);

		PROTORECVEVENT recv = { 0 };
		recv.flags = PREF_TCHAR;
		if (isRead)
			recv.flags |= PREF_CREATEREAD;
		if (isOut)
			recv.flags |= PREF_SENT;
		recv.timestamp = datetime;
		recv.tszMessage = ptszBody;
		recv.lParam = isOut;
		recv.pCustomData = szMid;
		recv.cbCustomDataSize = (int)strlen(szMid);
		ProtoChainRecvMsg(hContact, &recv);
	}

	MarkMessagesRead(mids);
	RetrieveMessagesByIds(lmids);
}
Exemple #12
0
void CMsnProto::getOIMs(ezxml_t xmli)
{
	ezxml_t toki = ezxml_child(xmli, "M");
	if (toki == NULL) return;

	char* getReqHdr;
	ezxml_t reqmsg;
	ezxml_t xmlreq = oimRecvHdr("GetMessage", reqmsg, getReqHdr);

	ezxml_t reqmid = ezxml_add_child(reqmsg, "messageId", 0);
	ezxml_t reqmrk = ezxml_add_child(reqmsg, "alsoMarkAsRead", 0);
	ezxml_set_txt(reqmrk, "false");

	char* delReqHdr;
	ezxml_t delmsg;
	ezxml_t xmldel = oimRecvHdr("DeleteMessages", delmsg, delReqHdr);
	ezxml_t delmids = ezxml_add_child(delmsg, "messageIds", 0);

	while (toki != NULL) {
		const char* szId = ezxml_txt(ezxml_child(toki, "I"));
		const char* szEmail = ezxml_txt(ezxml_child(toki, "E"));

		ezxml_set_txt(reqmid, szId);
		char* szData = ezxml_toxml(xmlreq, true);

		unsigned status;
		char* url = (char*)mir_strdup(oimRecvUrl);

		char* tResult = getSslResult(&url, szData, getReqHdr, status);

		free(szData);
		mir_free(url);

		if (tResult != NULL && status == 200) {
			ezxml_t xmlm = ezxml_parse_str(tResult, mir_strlen(tResult));
			ezxml_t body = getSoapResponse(xmlm, "GetMessage");

			MimeHeaders mailInfo;
			const char* mailbody = mailInfo.readFromBuffer((char*)ezxml_txt(body));

			time_t evtm = time(NULL);
			const char* arrTime = mailInfo["X-OriginalArrivalTime"];
			if (arrTime != NULL) {
				char szTime[32], *p;
				txtParseParam(arrTime, "FILETIME", "[", "]", szTime, sizeof(szTime));

				unsigned filetimeLo = strtoul(szTime, &p, 16);
				if (*p == ':') {
					unsigned __int64 filetime = strtoul(p + 1, &p, 16);
					filetime <<= 32;
					filetime |= filetimeLo;
					filetime /= 10000000;
#ifndef __GNUC__
					filetime -= 11644473600ui64;
#else
					filetime -= 11644473600ull;
#endif
					evtm = (time_t)filetime;
				}
			}

			PROTORECVEVENT pre = { 0 };
			pre.szMessage = mailInfo.decodeMailBody((char*)mailbody);
			pre.timestamp = evtm;
			ProtoChainRecvMsg(MSN_HContactFromEmail(szEmail), &pre);
			mir_free(pre.szMessage);

			ezxml_t delmid = ezxml_add_child(delmids, "messageId", 0);
			ezxml_set_txt(delmid, szId);

			ezxml_free(xmlm);
		}
		mir_free(tResult);
		toki = ezxml_next(toki);
	}
	ezxml_free(xmlreq);
	mir_free(getReqHdr);

	if (ezxml_child(delmids, "messageId") != NULL) {
		char* szData = ezxml_toxml(xmldel, true);

		unsigned status;
		char* url = (char*)mir_strdup(oimRecvUrl);

		char* tResult = getSslResult(&url, szData, delReqHdr, status);

		mir_free(url);
		mir_free(tResult);
		free(szData);
	}
	ezxml_free(xmldel);
	mir_free(delReqHdr);
}
Exemple #13
0
void CYahooProto::ext_got_im(const char *me, const char *who, int protocol, const char *msg, 
								long tm, int stat, int utf8, int buddy_icon, 
								const char *seqn, int sendn)
{
	char 		*umsg;
	const char	*c = msg;
	int 		oidx = 0;

	LOG(("YAHOO_GOT_IM id:%s %s: %s (len: %d) tm:%lu stat:%i utf8:%i buddy_icon: %i", me, who, msg, lstrlenA(msg), tm, stat, utf8, buddy_icon));

	if (stat == 2) {
		char z[1024];

		mir_snprintf(z, SIZEOF(z), "Error sending message to %s", who);
		LOG((z));
		ShowError( TranslateT("Yahoo Error"), _A2T(z));
		return;
	}

	if (!msg) {
		LOG(("Empty Incoming Message, exiting."));
		return;
	}

	if (getByte("IgnoreUnknown", 0)) {

		/*
		* Check our buddy list to see if we have it there. And if it's not on the list then we don't accept any IMs.
		*/
		if (getbuddyH(who) == NULL) {
			LOG(("Ignoring unknown user messages. User '%s'. Dropping Message.", who));
			return;
		}
	}

	if ( BuddyIgnored( who )) {
		LOG(("User '%s' on our Ignore List. Dropping Message.", who));
		return;
	}

	// make a bigger buffer for \n -> \r\n conversion (x2)
	umsg = (char *) alloca(lstrlenA(msg) * 2 + 1); 

	while ( *c != '\0') {
		// Strip the font tag
		if (!_strnicmp(c,"<font ",6) || !_strnicmp(c,"</font>",6) ||
			// strip the fade tag
			!_strnicmp(c, "<FADE ",6) || !_strnicmp(c,"</FADE>",7) ||
			// strip the alternate colors tag
			!_strnicmp(c, "<ALT ",5) || !_strnicmp(c, "</ALT>",6)) { 
				while ((*c++ != '>') && (*c != '\0')); 
		} else
			// strip ANSI color combination
			if ((*c == 0x1b) && (*(c+1) == '[')) { 
				while ((*c++ != 'm') && (*c != '\0')); 
			} else

				if (*c != '\0') {
					umsg[oidx++] = *c;

					/* Adding \r to \r\n conversion */
					if (*c == '\r' && *(c + 1) != '\n') 
						umsg[oidx++] = '\n';

					c++;
				}
	}

	umsg[oidx++]= '\0';

	/* Need to strip off formatting stuff first. Then do all decoding/converting */
	LOG(("%s: %s", who, umsg));

	HANDLE hContact = add_buddy(who, who, protocol, PALF_TEMPORARY);
	//setWord(hContact, "yprotoid", protocol);
	Set_Protocol(hContact, protocol);

	PROTORECVEVENT pre = { 0 };
	pre.flags = (utf8) ? PREF_UTF : 0;

	if (tm) {
		HANDLE hEvent = db_event_last(hContact);

		if (hEvent) { // contact has events
			DWORD dummy;
			DBEVENTINFO dbei = { sizeof (dbei) };
			dbei.pBlob = (BYTE*)&dummy;
			dbei.cbBlob = 2;
			if (!db_event_get(hEvent, &dbei)) 
				// got that event, if newer than ts then reset to current time
				if ((DWORD)tm < dbei.timestamp) tm = (long)time(NULL);
		}

		pre.timestamp = (DWORD)time(NULL);
		
		if ((DWORD)tm < pre.timestamp)
			pre.timestamp = tm;
		
	}
	else pre.timestamp = (DWORD)time(NULL);

	pre.szMessage = umsg;
	pre.lParam = 0;

	// Turn off typing
	CallService(MS_PROTO_CONTACTISTYPING, (WPARAM) hContact, PROTOTYPE_CONTACTTYPING_OFF);
	ProtoChainRecvMsg(hContact, &pre);

	// ack the message we just got
	if (seqn)
		yahoo_send_im_ack(m_id, me, who, seqn, sendn);

	if (buddy_icon < 0) return;

	//?? Don't generate floods!!
	setByte(hContact, "AvatarType", (BYTE)buddy_icon);
	if (buddy_icon != 2)
		reset_avatar(hContact);
	else if (getDword(hContact, "PictCK", 0) == 0) /* request the buddy image */
		request_avatar(who); 
}
void CVkProto::OnReceiveHistoryMessages(NETLIBHTTPREQUEST *reply, AsyncHttpRequest *pReq)
{
	debugLogA("CVkProto::OnReceiveHistoryMessages %d", reply->resultCode);
	if (reply->resultCode != 200 || !pReq->pUserInfo)
		return;

	JSONNode jnRoot;
	CVkSendMsgParam *param = (CVkSendMsgParam*)pReq->pUserInfo;
	const JSONNode &jnResponse = CheckJsonResponse(pReq, reply, jnRoot);
	if (!jnResponse) {
		if (!pReq->bNeedsRestart || m_bTerminated) {
			delete param;
			pReq->pUserInfo = NULL;
		}
		return;
	}
	
	int iTime = jnResponse["datetime"].as_int(); 
	const JSONNode &jnMsgs = jnResponse["items"];
	const JSONNode &jnFUsers = jnResponse["fwd_users"];

	int iLastMsgId = getDword(param->hContact, "lastmsgid", -1);
	time_t tLastReadMessageTime = 0;
	int count = 0;

	for (auto it = jnMsgs.rbegin(); it != jnMsgs.rend(); ++it) {
		const JSONNode &jnMsg = (*it);

		int mid = jnMsg["id"].as_int();
		if (iLastMsgId < mid) 
			iLastMsgId = mid;

		char szMid[40];
		_itoa(mid, szMid, 10);

		CMString tszBody(jnMsg["body"].as_mstring());
		int datetime = jnMsg["date"].as_int();
		int isOut = jnMsg["out"].as_int();
		int isRead = jnMsg["read_state"].as_int(); 
		int uid = jnMsg["user_id"].as_int(); 
		
		const JSONNode &jnFwdMessages = jnMsg["fwd_messages"];
		if (jnFwdMessages) {
			CMString tszFwdMessages = GetFwdMessages(jnFwdMessages, jnFUsers, m_iBBCForAttachments);
			if (!tszBody.IsEmpty())
				tszFwdMessages = _T("\n") + tszFwdMessages;
			tszBody += tszFwdMessages;
		}
		
		const JSONNode &jnAttachments = jnMsg["attachments"];
		if (jnAttachments) {
			CMString tszAttachmentDescr = GetAttachmentDescr(jnAttachments, m_iBBCForAttachments);
			if (!tszBody.IsEmpty())
				tszAttachmentDescr = _T("\n") + tszAttachmentDescr;
			tszBody += tszAttachmentDescr;
		}

		T2Utf pszBody(tszBody);
		MCONTACT hContact = FindUser(uid, true);
		PROTORECVEVENT recv = { 0 };
		if (isRead)
			recv.flags |= PREF_CREATEREAD;
		if (isOut)
			recv.flags |= PREF_SENT;
		recv.timestamp = datetime;
		recv.szMessage = pszBody;
		recv.lParam = isOut;
		recv.pCustomData = szMid;
		recv.cbCustomDataSize = (int)mir_strlen(szMid);
		ProtoChainRecvMsg(hContact, &recv);

		if (isRead && isOut && datetime > tLastReadMessageTime)
			tLastReadMessageTime = datetime;

		count++;
	}
	setDword(param->hContact, "lastmsgid", iLastMsgId);

	if (ServiceExists(MS_MESSAGESTATE_UPDATE)) {
		MessageReadData data(tLastReadMessageTime, MRD_TYPE_MESSAGETIME);
		CallService(MS_MESSAGESTATE_UPDATE, param->hContact, (LPARAM)&data);
	}

	int once = jnResponse["once"].as_int();
	int iRCount = jnResponse["rcount"].as_int();
	if (count == iRCount && once == 0)
		GetServerHistory(param->hContact, param->iCount + count, iRCount, iTime, param->iMsgID);

	if (!pReq->bNeedsRestart || m_bTerminated) {
		delete param;
		pReq->pUserInfo = NULL;
	}
}
Exemple #15
0
void CVkProto::OnReceiveHistoryMessages(NETLIBHTTPREQUEST *reply, AsyncHttpRequest *pReq)
{
	debugLogA("CVkProto::OnReceiveHistoryMessages %d", reply->resultCode);
	if (reply->resultCode != 200 || !pReq->pUserInfo) {
		mir_cslock lck(m_csLoadHistoryTask);
		if (m_iLoadHistoryTask > 0)
			m_iLoadHistoryTask--;
		debugLog(_T("CVkProto::OnReceiveHistoryMessages error m_iLoadHistoryTask=%d"), m_iLoadHistoryTask);
		MsgPopup(NULL, TranslateT("Error loading message history from server"), TranslateT("Error"), true);

		if (m_iLoadHistoryTask == 0 && m_bNotifyForEndLoadingHistoryAllContact) {
			MsgPopup(NULL, TranslateT("Loading messages for all contacts is completed"), TranslateT("Loading history"));
			m_bNotifyForEndLoadingHistoryAllContact = m_bNotifyForEndLoadingHistory = false;
		}

		return;
	}

	JSONNode jnRoot;
	CVkSendMsgParam *param = (CVkSendMsgParam*)pReq->pUserInfo;
	const JSONNode &jnResponse = CheckJsonResponse(pReq, reply, jnRoot);
	if (!jnResponse) {
		if (!pReq->bNeedsRestart || m_bTerminated) {
			mir_cslock lck(m_csLoadHistoryTask);
			if (m_iLoadHistoryTask > 0) 
				m_iLoadHistoryTask--;
			
			ptrT ptszNick(db_get_tsa(param->hContact, m_szModuleName, "Nick"));
			CMString str(FORMAT, _T("%s %s %s"), TranslateT("Error loading message history from server"), TranslateT("for"), ptszNick);

			MsgPopup(param->hContact, str, TranslateT("Error"), true);
			debugLog(_T("CVkProto::OnReceiveHistoryMessages error for %s m_iLoadHistoryTask=%d"), ptszNick, m_iLoadHistoryTask);

			if (m_iLoadHistoryTask == 0 && m_bNotifyForEndLoadingHistoryAllContact) {
				MsgPopup(NULL, TranslateT("Loading messages for all contacts is completed"), TranslateT("Loading history"));
				m_bNotifyForEndLoadingHistoryAllContact = m_bNotifyForEndLoadingHistory = false;
			}

			delete param;
			pReq->pUserInfo = NULL;
		}
		return;
	}

	int iTime = jnResponse["datetime"].as_int(); 
	const JSONNode &jnMsgs = jnResponse["items"];
	const JSONNode &jnFUsers = jnResponse["fwd_users"];

	int iLastMsgId = getDword(param->hContact, "lastmsgid", -1);
	time_t tLastReadMessageTime = 0;
	int count = 0;

	for (auto it = jnMsgs.rbegin(); it != jnMsgs.rend(); ++it) {
		const JSONNode &jnMsg = (*it);

		int mid = jnMsg["id"].as_int();
		if (iLastMsgId < mid) 
			iLastMsgId = mid;

		char szMid[40];
		_itoa(mid, szMid, 10);

		CMString tszBody(jnMsg["body"].as_mstring());
		int datetime = jnMsg["date"].as_int();
		int isOut = jnMsg["out"].as_int();
		int isRead = jnMsg["read_state"].as_int(); 
		int uid = jnMsg["user_id"].as_int(); 

		const JSONNode &jnFwdMessages = jnMsg["fwd_messages"];
		if (jnFwdMessages) {
			CMString tszFwdMessages = GetFwdMessages(jnFwdMessages, jnFUsers, m_vkOptions.BBCForAttachments());
			if (!tszBody.IsEmpty())
				tszFwdMessages = _T("\n") + tszFwdMessages;
			tszBody += tszFwdMessages;
		}

		const JSONNode &jnAttachments = jnMsg["attachments"];
		if (jnAttachments) {
			CMString tszAttachmentDescr = GetAttachmentDescr(jnAttachments, m_vkOptions.BBCForAttachments());
			if (!tszBody.IsEmpty())
				tszAttachmentDescr = _T("\n") + tszAttachmentDescr;
			tszBody += tszAttachmentDescr;
		}

		T2Utf pszBody(tszBody);
		MCONTACT hContact = FindUser(uid, true);
		PROTORECVEVENT recv = { 0 };
		if (isRead)
			recv.flags |= PREF_CREATEREAD;
		if (isOut)
			recv.flags |= PREF_SENT;
		recv.timestamp = datetime;
		recv.szMessage = pszBody;
		recv.lParam = isOut;
		recv.pCustomData = szMid;
		recv.cbCustomDataSize = (int)mir_strlen(szMid);
		ProtoChainRecvMsg(hContact, &recv);

		if (isRead && isOut && datetime > tLastReadMessageTime)
			tLastReadMessageTime = datetime;

		count++;
	}
	setDword(param->hContact, "lastmsgid", iLastMsgId);

	if (ServiceExists(MS_MESSAGESTATE_UPDATE)) {
		MessageReadData data(tLastReadMessageTime, MRD_TYPE_MESSAGETIME);
		CallService(MS_MESSAGESTATE_UPDATE, param->hContact, (LPARAM)&data);
	}

	int once = jnResponse["once"].as_int();
	int iRCount = jnResponse["rcount"].as_int();
	if (count == iRCount && once == 0)
		GetServerHistory(param->hContact, param->iCount + count, iRCount, iTime, param->iMsgID);
	else {
		mir_cslock lck(m_csLoadHistoryTask);
		if (m_iLoadHistoryTask > 0)
			m_iLoadHistoryTask--;

		ptrT ptszNick(db_get_tsa(param->hContact, m_szModuleName, "Nick"));
		CMString str(FORMAT, TranslateT("Loading messages for %s is completed"), ptszNick);
		debugLog(_T("CVkProto::OnReceiveHistoryMessages for %s m_iLoadHistoryTask=%d"), ptszNick, m_iLoadHistoryTask);

		if (m_bNotifyForEndLoadingHistory)
			MsgPopup(param->hContact, str, TranslateT("Loading history"));

		if (m_iLoadHistoryTask == 0 && m_bNotifyForEndLoadingHistoryAllContact) {
			MsgPopup(NULL, TranslateT("Loading messages for all contacts is completed"), TranslateT("Loading history"));
			m_bNotifyForEndLoadingHistoryAllContact = m_bNotifyForEndLoadingHistory = false;		
		}
	}

	if (!pReq->bNeedsRestart || m_bTerminated) {
		delete param;
		pReq->pUserInfo = NULL;
	}
}