2012-12-02 14:40:17 -05:00
|
|
|
|
|
|
|
#include <algorithm>
|
|
|
|
#include <math.h>
|
2012-12-05 17:45:44 -05:00
|
|
|
#include <sstream>
|
2012-12-09 07:12:57 -05:00
|
|
|
#include <stdio.h>
|
2012-12-02 14:40:17 -05:00
|
|
|
|
2012-10-05 14:12:52 -04:00
|
|
|
#include "p3posted.h"
|
2013-02-28 16:58:38 -05:00
|
|
|
#include "retroshare/rsgxsflags.h"
|
2012-10-21 15:45:35 -04:00
|
|
|
#include "serialiser/rsposteditems.h"
|
|
|
|
|
2012-12-08 16:50:13 -05:00
|
|
|
#define UPDATE_PHASE_GRP_REQUEST 1
|
|
|
|
#define UPDATE_PHASE_MSG_REQUEST 2
|
|
|
|
#define UPDATE_PHASE_VOTE_COMMENT_REQUEST 3
|
|
|
|
#define UPDATE_PHASE_VOTE_COUNT 4
|
|
|
|
#define UPDATE_PHASE_COMMENT_COUNT 5
|
|
|
|
#define UPDATE_PHASE_COMPLETE 6
|
|
|
|
|
2012-12-12 17:41:21 -05:00
|
|
|
#define NUM_TOPICS_TO_GENERATE 5
|
2012-12-11 17:26:11 -05:00
|
|
|
#define NUM_POSTS_TO_GENERATE 7
|
|
|
|
#define NUM_VOTES_TO_GENERATE 11
|
2012-12-15 19:43:15 -05:00
|
|
|
#define NUM_COMMENTS_TO_GENERATE 3
|
2012-12-05 17:45:44 -05:00
|
|
|
|
2012-12-11 17:26:11 -05:00
|
|
|
#define VOTE_UPDATE_PERIOD 5 // 20 seconds
|
2012-12-15 19:43:15 -05:00
|
|
|
#define HOT_PERIOD 4 // 4 secs for testing prob 1 to 2 days in practice
|
2012-12-08 16:50:13 -05:00
|
|
|
|
2012-10-21 15:45:35 -04:00
|
|
|
const uint32_t RsPosted::FLAG_MSGTYPE_COMMENT = 0x0001;
|
|
|
|
const uint32_t RsPosted::FLAG_MSGTYPE_POST = 0x0002;
|
|
|
|
const uint32_t RsPosted::FLAG_MSGTYPE_VOTE = 0x0004;
|
2012-12-02 14:40:17 -05:00
|
|
|
const uint32_t RsPosted::FLAG_MSGTYPE_MASK = 0x000f;
|
|
|
|
|
|
|
|
#define POSTED_MAX_SERVICE_STRING 50
|
2012-10-21 15:45:35 -04:00
|
|
|
|
|
|
|
RsPosted *rsPosted = NULL;
|
2012-10-05 14:12:52 -04:00
|
|
|
|
2012-11-25 16:50:45 -05:00
|
|
|
RsPostedComment::RsPostedComment(const RsGxsPostedCommentItem & item)
|
|
|
|
{
|
|
|
|
mComment = item.mComment.mComment;
|
|
|
|
mMeta = item.meta;
|
|
|
|
}
|
|
|
|
|
2012-12-02 14:40:17 -05:00
|
|
|
RsPostedVote::RsPostedVote(const RsGxsPostedVoteItem& item)
|
|
|
|
{
|
|
|
|
mDirection = item.mVote.mDirection;
|
|
|
|
mMeta = item.meta;
|
|
|
|
}
|
|
|
|
|
2012-10-05 14:12:52 -04:00
|
|
|
p3Posted::p3Posted(RsGeneralDataService *gds, RsNetworkExchangeService *nes)
|
2012-12-02 14:40:17 -05:00
|
|
|
: RsGenExchange(gds, nes, new RsGxsPostedSerialiser(), RS_SERVICE_GXSV1_TYPE_POSTED), RsPosted(this), mPostedMutex("Posted"),
|
2012-12-09 17:38:49 -05:00
|
|
|
mTokenService(NULL), mGeneratingTopics(true), mGeneratingPosts(false), mRequestPhase1(true), mRequestPhase2(false),
|
|
|
|
mRequestPhase3(false), mGenerateVotesAndComments(false)
|
2012-10-05 14:12:52 -04:00
|
|
|
{
|
2012-12-08 16:50:13 -05:00
|
|
|
mPostUpdate = false;
|
|
|
|
mLastUpdate = time(NULL);
|
|
|
|
mUpdatePhase = UPDATE_PHASE_GRP_REQUEST;
|
|
|
|
|
2012-12-02 14:40:17 -05:00
|
|
|
mTokenService = RsGenExchange::getTokenService();
|
2012-10-05 14:12:52 -04:00
|
|
|
}
|
|
|
|
|
|
|
|
void p3Posted::notifyChanges(std::vector<RsGxsNotify *> &changes)
|
|
|
|
{
|
2013-02-28 16:58:38 -05:00
|
|
|
RsGxsIfaceHelper::receiveChanges(changes);
|
2012-10-05 14:12:52 -04:00
|
|
|
}
|
|
|
|
|
2012-10-21 15:45:35 -04:00
|
|
|
void p3Posted::service_tick()
|
2012-10-05 14:12:52 -04:00
|
|
|
{
|
2012-12-08 16:50:13 -05:00
|
|
|
|
2013-02-10 10:40:07 -05:00
|
|
|
#ifndef GXS_DEV_TESTNET // DISABLE DUMMYDATA if TEST_NET
|
|
|
|
|
2012-12-05 17:45:44 -05:00
|
|
|
generateTopics();
|
2012-12-08 16:50:13 -05:00
|
|
|
generatePosts();
|
2012-12-09 17:38:49 -05:00
|
|
|
generateVotesAndComments();
|
2012-12-08 16:50:13 -05:00
|
|
|
|
2013-02-10 10:40:07 -05:00
|
|
|
#endif
|
|
|
|
|
2013-02-07 18:04:16 -05:00
|
|
|
// time_t now = time(NULL);
|
|
|
|
//
|
|
|
|
// if((now > (time_t) (VOTE_UPDATE_PERIOD + mLastUpdate)) &&
|
|
|
|
// (mUpdatePhase == UPDATE_PHASE_GRP_REQUEST))
|
|
|
|
// {
|
|
|
|
// mPostUpdate = true;
|
|
|
|
// mLastUpdate = time(NULL);
|
|
|
|
// }
|
|
|
|
//
|
|
|
|
// updateVotes();
|
|
|
|
//
|
|
|
|
// processRankings();
|
2012-12-05 17:45:44 -05:00
|
|
|
}
|
|
|
|
|
2012-12-09 17:38:49 -05:00
|
|
|
void p3Posted::generateVotesAndComments()
|
|
|
|
{
|
|
|
|
if(mGenerateVotesAndComments)
|
|
|
|
{
|
|
|
|
|
|
|
|
if(mRequestPhase1)
|
|
|
|
{
|
|
|
|
// request topics then chose at random which one to use to generate a post about
|
|
|
|
RsTokReqOptions opts;
|
|
|
|
opts.mReqType = GXS_REQUEST_TYPE_MSG_IDS;
|
|
|
|
opts.mMsgFlagFilter = RsPosted::FLAG_MSGTYPE_POST;
|
|
|
|
opts.mMsgFlagMask = RsPosted::FLAG_MSGTYPE_MASK;
|
|
|
|
|
|
|
|
mTokenService->requestMsgInfo(mToken, 0, opts, mGrpIds);
|
|
|
|
mRequestPhase1 = false;
|
|
|
|
mRequestPhase2 = true;
|
|
|
|
return;
|
|
|
|
}
|
|
|
|
|
|
|
|
if(mRequestPhase2)
|
|
|
|
{
|
|
|
|
|
|
|
|
if(mTokenService->requestStatus(mToken) == RsTokenService::GXS_REQUEST_V2_STATUS_COMPLETE)
|
|
|
|
{
|
|
|
|
GxsMsgIdResult msgIds;
|
|
|
|
RsGenExchange::getMsgList(mToken, msgIds);
|
|
|
|
|
|
|
|
// for each msg generate a random number of votes and comments
|
|
|
|
|
|
|
|
|
|
|
|
GxsMsgIdResult::iterator mit = msgIds.begin();
|
|
|
|
|
|
|
|
for(; mit != msgIds.end(); mit++)
|
|
|
|
{
|
|
|
|
const RsGxsGroupId& grpId = mit->first;
|
|
|
|
std::vector<RsGxsMessageId>& msgIdsV = mit->second;
|
|
|
|
std::vector<RsGxsMessageId>::iterator vit = msgIdsV.begin();
|
|
|
|
|
|
|
|
for(; vit != msgIdsV.end(); vit++)
|
|
|
|
{
|
|
|
|
const RsGxsMessageId& msgId = *vit;
|
|
|
|
|
|
|
|
int nVotes = rand()%NUM_VOTES_TO_GENERATE;
|
|
|
|
uint32_t token;
|
|
|
|
|
|
|
|
for(int i=1; i < nVotes; i++)
|
|
|
|
{
|
|
|
|
RsPostedVote v;
|
|
|
|
|
|
|
|
v.mDirection = (rand()%10 > 3) ? 0 : 1;
|
|
|
|
v.mMeta.mParentId = msgId;
|
|
|
|
v.mMeta.mGroupId = grpId;
|
|
|
|
|
|
|
|
std::ostringstream ostrm;
|
|
|
|
ostrm << i;
|
|
|
|
|
|
|
|
v.mMeta.mMsgName = "Vote " + ostrm.str();
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
submitVote(token, v);
|
|
|
|
mTokens.push_back(token);
|
|
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
int nComments = rand()%NUM_COMMENTS_TO_GENERATE;
|
|
|
|
|
|
|
|
// single level comments for now
|
|
|
|
for(int i=1; i < nComments; i++)
|
|
|
|
{
|
|
|
|
RsPostedComment c;
|
|
|
|
|
|
|
|
std::ostringstream ostrm;
|
|
|
|
ostrm << i;
|
|
|
|
|
|
|
|
c.mComment = "Comment " + ostrm.str();
|
|
|
|
c.mMeta.mParentId = msgId;
|
|
|
|
c.mMeta.mGroupId = grpId;
|
2012-12-11 17:26:11 -05:00
|
|
|
c.mMeta.mThreadId = msgId;
|
2012-12-09 17:38:49 -05:00
|
|
|
|
|
|
|
submitComment(token, c);
|
|
|
|
mTokens.push_back(token);
|
|
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
}
|
|
|
|
}
|
|
|
|
mRequestPhase2 = false;
|
|
|
|
mRequestPhase3 = true;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
if(mRequestPhase3)
|
|
|
|
{
|
|
|
|
if(!mTokens.empty())
|
|
|
|
{
|
|
|
|
std::vector<uint32_t>::iterator vit = mTokens.begin();
|
|
|
|
|
|
|
|
for(; vit != mTokens.end(); )
|
|
|
|
{
|
|
|
|
if(mTokenService->requestStatus(*vit) == RsTokenService::GXS_REQUEST_V2_STATUS_COMPLETE)
|
|
|
|
vit = mTokens.erase(vit);
|
|
|
|
else
|
|
|
|
vit++;
|
|
|
|
}
|
|
|
|
}else
|
|
|
|
{
|
|
|
|
// stop generating posts after acknowledging all the ones you created
|
|
|
|
mGeneratingPosts = false;
|
|
|
|
mRequestPhase3 = false;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2012-12-05 17:45:44 -05:00
|
|
|
void p3Posted::generatePosts()
|
|
|
|
{
|
|
|
|
if(mGeneratingPosts)
|
|
|
|
{
|
|
|
|
|
|
|
|
|
2012-12-08 16:50:13 -05:00
|
|
|
if(mRequestPhase1)
|
|
|
|
{
|
|
|
|
// request topics then chose at random which one to use to generate a post about
|
|
|
|
RsTokReqOptions opts;
|
|
|
|
opts.mReqType = GXS_REQUEST_TYPE_GROUP_IDS;
|
|
|
|
mTokenService->requestGroupInfo(mToken, 0, opts);
|
|
|
|
mRequestPhase1 = false;
|
|
|
|
return;
|
|
|
|
}
|
|
|
|
else if(!mRequestPhase2)
|
|
|
|
{
|
|
|
|
if(mTokenService->requestStatus(mToken) == RsTokenService::GXS_REQUEST_V2_STATUS_COMPLETE)
|
|
|
|
{
|
|
|
|
RsGenExchange::getGroupList(mToken, mGrpIds);
|
2012-12-05 17:45:44 -05:00
|
|
|
|
2012-12-08 16:50:13 -05:00
|
|
|
mRequestPhase2 = true;
|
|
|
|
}
|
|
|
|
}
|
2012-12-05 17:45:44 -05:00
|
|
|
|
2012-12-08 16:50:13 -05:00
|
|
|
if(mRequestPhase2)
|
2012-12-05 17:45:44 -05:00
|
|
|
{
|
2012-12-08 16:50:13 -05:00
|
|
|
// for each group generate NUM_POSTS_TO_GENERATE posts
|
|
|
|
std::list<RsGxsGroupId>::iterator lit = mGrpIds.begin();
|
2012-12-05 17:45:44 -05:00
|
|
|
|
2012-12-08 16:50:13 -05:00
|
|
|
for(; lit != mGrpIds.end(); lit++)
|
2012-12-05 17:45:44 -05:00
|
|
|
{
|
2012-12-08 16:50:13 -05:00
|
|
|
RsGxsGroupId& grpId = *lit;
|
|
|
|
|
|
|
|
for(int i=0; i < NUM_POSTS_TO_GENERATE; i++)
|
|
|
|
{
|
|
|
|
std::ostringstream ostrm;
|
|
|
|
ostrm << i;
|
|
|
|
std::string link = "link " + ostrm.str();
|
|
|
|
|
|
|
|
RsPostedPost post;
|
|
|
|
post.mLink = link;
|
|
|
|
post.mNotes = link;
|
|
|
|
post.mMeta.mMsgName = link;
|
|
|
|
post.mMeta.mGroupId = grpId;
|
|
|
|
|
|
|
|
uint32_t token;
|
|
|
|
submitPost(token, post);
|
|
|
|
mTokens.push_back(token);
|
|
|
|
}
|
2012-12-05 17:45:44 -05:00
|
|
|
}
|
|
|
|
|
2012-12-08 16:50:13 -05:00
|
|
|
mRequestPhase2 = false;
|
|
|
|
mRequestPhase3 = true;
|
|
|
|
|
|
|
|
}
|
|
|
|
else if(mRequestPhase3)
|
|
|
|
{
|
|
|
|
|
|
|
|
if(!mTokens.empty())
|
2012-12-05 17:45:44 -05:00
|
|
|
{
|
2012-12-08 16:50:13 -05:00
|
|
|
std::vector<uint32_t>::iterator vit = mTokens.begin();
|
2012-12-05 17:45:44 -05:00
|
|
|
|
2012-12-08 16:50:13 -05:00
|
|
|
for(; vit != mTokens.end(); )
|
2012-12-05 17:45:44 -05:00
|
|
|
{
|
2012-12-08 16:50:13 -05:00
|
|
|
if(mTokenService->requestStatus(*vit) == RsTokenService::GXS_REQUEST_V2_STATUS_COMPLETE)
|
|
|
|
vit = mTokens.erase(vit);
|
2012-12-05 17:45:44 -05:00
|
|
|
else
|
|
|
|
vit++;
|
|
|
|
}
|
2012-12-08 16:50:13 -05:00
|
|
|
}else
|
|
|
|
{
|
|
|
|
// stop generating posts after acknowledging all the ones you created
|
|
|
|
mGeneratingPosts = false;
|
|
|
|
mRequestPhase3 = false;
|
2012-12-09 17:38:49 -05:00
|
|
|
mGenerateVotesAndComments = true;
|
|
|
|
mRequestPhase1 = true;
|
2012-12-05 17:45:44 -05:00
|
|
|
}
|
|
|
|
|
2012-12-08 16:50:13 -05:00
|
|
|
}
|
2012-12-05 17:45:44 -05:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
void p3Posted::generateTopics()
|
|
|
|
{
|
|
|
|
if(mGeneratingTopics)
|
|
|
|
{
|
2012-12-08 16:50:13 -05:00
|
|
|
if(mRequestPhase1)
|
2012-12-05 17:45:44 -05:00
|
|
|
{
|
|
|
|
|
|
|
|
|
2012-12-08 16:50:13 -05:00
|
|
|
for(int i=0; i < NUM_TOPICS_TO_GENERATE; i++)
|
|
|
|
{
|
|
|
|
std::ostringstream strm;
|
|
|
|
strm << i;
|
|
|
|
std::string topicName = "Topic " + strm.str();
|
|
|
|
|
|
|
|
RsPostedGroup topic;
|
|
|
|
topic.mMeta.mGroupName = topicName;
|
2012-12-05 17:45:44 -05:00
|
|
|
|
2012-12-08 16:50:13 -05:00
|
|
|
uint32_t token;
|
|
|
|
submitGroup(token, topic);
|
|
|
|
mTokens.push_back(token);
|
|
|
|
}
|
2012-12-05 17:45:44 -05:00
|
|
|
|
2012-12-08 16:50:13 -05:00
|
|
|
mRequestPhase1 = false;
|
|
|
|
}
|
|
|
|
else
|
2012-12-05 17:45:44 -05:00
|
|
|
{
|
|
|
|
|
2012-12-08 16:50:13 -05:00
|
|
|
if(!mTokens.empty())
|
|
|
|
{
|
|
|
|
std::vector<uint32_t>::iterator vit = mTokens.begin();
|
|
|
|
|
|
|
|
for(; vit != mTokens.end(); )
|
|
|
|
{
|
|
|
|
if(mTokenService->requestStatus(*vit) == RsTokenService::GXS_REQUEST_V2_STATUS_COMPLETE)
|
|
|
|
{
|
|
|
|
RsGxsGroupId grpId;
|
|
|
|
RsGenExchange::acknowledgeTokenGrp(*vit, grpId);
|
|
|
|
vit = mTokens.erase(vit);
|
|
|
|
}
|
|
|
|
else
|
|
|
|
vit++;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
else
|
2012-12-05 17:45:44 -05:00
|
|
|
{
|
2012-12-08 16:50:13 -05:00
|
|
|
mGeneratingPosts = true;
|
|
|
|
mGeneratingTopics = false;
|
|
|
|
mRequestPhase1 = true;
|
2012-12-05 17:45:44 -05:00
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
2012-10-05 14:12:52 -04:00
|
|
|
}
|
|
|
|
|
2012-10-21 15:45:35 -04:00
|
|
|
bool p3Posted::getGroup(const uint32_t &token, std::vector<RsPostedGroup> &groups)
|
2012-10-05 14:12:52 -04:00
|
|
|
{
|
2012-10-21 15:45:35 -04:00
|
|
|
std::vector<RsGxsGrpItem*> grpData;
|
|
|
|
bool ok = RsGenExchange::getGroupData(token, grpData);
|
2012-10-05 14:12:52 -04:00
|
|
|
|
2012-10-21 15:45:35 -04:00
|
|
|
if(ok)
|
|
|
|
{
|
|
|
|
std::vector<RsGxsGrpItem*>::iterator vit = grpData.begin();
|
2012-10-05 14:12:52 -04:00
|
|
|
|
2012-10-21 15:45:35 -04:00
|
|
|
for(; vit != grpData.end(); vit++)
|
|
|
|
{
|
|
|
|
RsGxsPostedGroupItem* item = dynamic_cast<RsGxsPostedGroupItem*>(*vit);
|
|
|
|
RsPostedGroup grp = item->mGroup;
|
|
|
|
item->mGroup.mMeta = item->meta;
|
|
|
|
grp.mMeta = item->mGroup.mMeta;
|
|
|
|
delete item;
|
|
|
|
groups.push_back(grp);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
return ok;
|
2012-10-05 14:12:52 -04:00
|
|
|
}
|
|
|
|
|
2012-10-21 15:45:35 -04:00
|
|
|
bool p3Posted::getPost(const uint32_t &token, PostedPostResult &posts)
|
2012-10-05 14:12:52 -04:00
|
|
|
{
|
2012-10-21 15:45:35 -04:00
|
|
|
GxsMsgDataMap msgData;
|
|
|
|
bool ok = RsGenExchange::getMsgData(token, msgData);
|
2012-10-05 14:12:52 -04:00
|
|
|
|
2012-10-21 15:45:35 -04:00
|
|
|
if(ok)
|
|
|
|
{
|
|
|
|
GxsMsgDataMap::iterator mit = msgData.begin();
|
2012-10-05 14:12:52 -04:00
|
|
|
|
2012-10-21 15:45:35 -04:00
|
|
|
for(; mit != msgData.end(); mit++)
|
|
|
|
{
|
|
|
|
RsGxsGroupId grpId = mit->first;
|
|
|
|
std::vector<RsGxsMsgItem*>& msgItems = mit->second;
|
|
|
|
std::vector<RsGxsMsgItem*>::iterator vit = msgItems.begin();
|
2012-10-05 14:12:52 -04:00
|
|
|
|
2012-10-21 15:45:35 -04:00
|
|
|
for(; vit != msgItems.end(); vit++)
|
|
|
|
{
|
|
|
|
RsGxsPostedPostItem* item = dynamic_cast<RsGxsPostedPostItem*>(*vit);
|
2012-10-05 14:12:52 -04:00
|
|
|
|
2012-10-21 15:45:35 -04:00
|
|
|
if(item)
|
|
|
|
{
|
|
|
|
RsPostedPost post = item->mPost;
|
|
|
|
post.mMeta = item->meta;
|
|
|
|
posts[grpId].push_back(post);
|
|
|
|
delete item;
|
|
|
|
}else
|
|
|
|
{
|
|
|
|
std::cerr << "Not a post Item, deleting!" << std::endl;
|
|
|
|
delete *vit;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
2012-10-05 14:12:52 -04:00
|
|
|
|
2012-10-21 15:45:35 -04:00
|
|
|
return ok;
|
2012-10-05 14:12:52 -04:00
|
|
|
}
|
|
|
|
|
2012-10-21 15:45:35 -04:00
|
|
|
bool p3Posted::getComment(const uint32_t &token, PostedCommentResult &comments)
|
2012-10-05 14:12:52 -04:00
|
|
|
{
|
2012-10-21 15:45:35 -04:00
|
|
|
GxsMsgDataMap msgData;
|
|
|
|
bool ok = RsGenExchange::getMsgData(token, msgData);
|
2012-10-05 14:12:52 -04:00
|
|
|
|
2012-10-21 15:45:35 -04:00
|
|
|
if(ok)
|
|
|
|
{
|
|
|
|
GxsMsgDataMap::iterator mit = msgData.begin();
|
2012-10-05 14:12:52 -04:00
|
|
|
|
2012-10-21 15:45:35 -04:00
|
|
|
for(; mit != msgData.end(); mit++)
|
|
|
|
{
|
|
|
|
RsGxsGroupId grpId = mit->first;
|
|
|
|
std::vector<RsGxsMsgItem*>& msgItems = mit->second;
|
|
|
|
std::vector<RsGxsMsgItem*>::iterator vit = msgItems.begin();
|
2012-10-05 14:12:52 -04:00
|
|
|
|
2012-10-21 15:45:35 -04:00
|
|
|
for(; vit != msgItems.end(); vit++)
|
|
|
|
{
|
|
|
|
RsGxsPostedCommentItem* item = dynamic_cast<RsGxsPostedCommentItem*>(*vit);
|
2012-10-05 14:12:52 -04:00
|
|
|
|
2012-10-21 15:45:35 -04:00
|
|
|
if(item)
|
|
|
|
{
|
|
|
|
RsPostedComment comment = item->mComment;
|
|
|
|
comment.mMeta = item->meta;
|
|
|
|
comments[grpId].push_back(comment);
|
|
|
|
delete item;
|
|
|
|
}else
|
|
|
|
{
|
|
|
|
std::cerr << "Not a comment Item, deleting!" << std::endl;
|
|
|
|
delete *vit;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
2012-10-05 14:12:52 -04:00
|
|
|
|
2012-10-21 15:45:35 -04:00
|
|
|
return ok;
|
2012-10-05 14:12:52 -04:00
|
|
|
}
|
|
|
|
|
2012-11-25 16:50:45 -05:00
|
|
|
bool p3Posted::getRelatedComment(const uint32_t& token, PostedRelatedCommentResult &comments)
|
|
|
|
{
|
|
|
|
return RsGenExchange::getMsgRelatedDataT<RsGxsPostedCommentItem, RsPostedComment>(token, comments);
|
|
|
|
}
|
|
|
|
|
2012-10-21 15:45:35 -04:00
|
|
|
bool p3Posted::submitGroup(uint32_t &token, RsPostedGroup &group)
|
2012-10-05 14:12:52 -04:00
|
|
|
{
|
2012-10-21 15:45:35 -04:00
|
|
|
RsGxsPostedGroupItem* grpItem = new RsGxsPostedGroupItem();
|
|
|
|
grpItem->mGroup = group;
|
|
|
|
grpItem->meta = group.mMeta;
|
|
|
|
RsGenExchange::publishGroup(token, grpItem);
|
|
|
|
return true;
|
2012-10-05 14:12:52 -04:00
|
|
|
}
|
|
|
|
|
2012-10-21 15:45:35 -04:00
|
|
|
bool p3Posted::submitPost(uint32_t &token, RsPostedPost &post)
|
2012-10-05 14:12:52 -04:00
|
|
|
{
|
2012-10-21 15:45:35 -04:00
|
|
|
RsGxsPostedPostItem* postItem = new RsGxsPostedPostItem();
|
|
|
|
postItem->mPost = post;
|
|
|
|
postItem->meta = post.mMeta;
|
|
|
|
postItem->meta.mMsgFlags |= FLAG_MSGTYPE_POST;
|
2012-10-05 14:12:52 -04:00
|
|
|
|
2012-10-21 15:45:35 -04:00
|
|
|
RsGenExchange::publishMsg(token, postItem);
|
|
|
|
return true;
|
2012-10-05 14:12:52 -04:00
|
|
|
}
|
|
|
|
|
2012-10-21 15:45:35 -04:00
|
|
|
bool p3Posted::submitVote(uint32_t &token, RsPostedVote &vote)
|
2012-10-05 14:12:52 -04:00
|
|
|
{
|
2012-10-21 15:45:35 -04:00
|
|
|
RsGxsPostedVoteItem* voteItem = new RsGxsPostedVoteItem();
|
|
|
|
voteItem->mVote = vote;
|
|
|
|
voteItem->meta = vote.mMeta;
|
2012-12-02 14:40:17 -05:00
|
|
|
voteItem->meta.mMsgFlags |= FLAG_MSGTYPE_VOTE;
|
2012-10-05 14:12:52 -04:00
|
|
|
|
2012-10-21 15:45:35 -04:00
|
|
|
RsGenExchange::publishMsg(token, voteItem);
|
|
|
|
return true;
|
2012-10-05 14:12:52 -04:00
|
|
|
}
|
|
|
|
|
2012-10-21 15:45:35 -04:00
|
|
|
bool p3Posted::submitComment(uint32_t &token, RsPostedComment &comment)
|
2012-10-05 14:12:52 -04:00
|
|
|
{
|
2012-10-21 15:45:35 -04:00
|
|
|
RsGxsPostedCommentItem* commentItem = new RsGxsPostedCommentItem();
|
|
|
|
commentItem->mComment = comment;
|
|
|
|
commentItem->meta = comment.mMeta;
|
|
|
|
commentItem->meta.mMsgFlags |= FLAG_MSGTYPE_COMMENT;
|
2012-10-05 14:12:52 -04:00
|
|
|
|
2012-10-21 15:45:35 -04:00
|
|
|
RsGenExchange::publishMsg(token, commentItem);
|
|
|
|
return true;
|
2012-10-05 14:12:52 -04:00
|
|
|
}
|
|
|
|
|
2012-10-21 15:45:35 -04:00
|
|
|
// Special Ranking Request.
|
2012-11-30 13:54:25 -05:00
|
|
|
bool p3Posted::requestCommentRankings(uint32_t &token, const RankType &rType, const RsGxsGrpMsgIdPair &msgId)
|
|
|
|
{
|
|
|
|
token = RsGenExchange::generatePublicToken();
|
|
|
|
|
|
|
|
RsStackMutex stack(mPostedMutex);
|
|
|
|
|
|
|
|
GxsPostedCommentRanking* gpc = new GxsPostedCommentRanking();
|
|
|
|
gpc->msgId = msgId;
|
|
|
|
gpc->rType = rType;
|
|
|
|
gpc->pubToken = token;
|
|
|
|
|
|
|
|
mPendingCommentRanks.insert(std::make_pair(token, gpc));
|
|
|
|
|
|
|
|
return true;
|
|
|
|
}
|
|
|
|
|
2012-12-11 17:26:11 -05:00
|
|
|
bool p3Posted::requestPostRankings(uint32_t &token, const RankType &rType, const RsGxsGroupId &groupId)
|
2012-11-30 13:54:25 -05:00
|
|
|
{
|
|
|
|
token = RsGenExchange::generatePublicToken();
|
|
|
|
|
|
|
|
RsStackMutex stack(mPostedMutex);
|
|
|
|
GxsPostedPostRanking* gp = new GxsPostedPostRanking();
|
|
|
|
gp->grpId = groupId;
|
|
|
|
gp->rType = rType;
|
|
|
|
gp->pubToken = token;
|
2012-12-11 17:26:11 -05:00
|
|
|
gp->rankingResult.rType = gp->rType;
|
2012-12-12 17:41:21 -05:00
|
|
|
gp->rankingResult.grpId = gp->grpId;
|
2012-11-30 13:54:25 -05:00
|
|
|
|
2012-12-11 17:26:11 -05:00
|
|
|
mPendingPostRanks.push_back(gp);
|
2012-11-30 13:54:25 -05:00
|
|
|
|
|
|
|
return true;
|
|
|
|
}
|
|
|
|
|
2012-12-11 17:26:11 -05:00
|
|
|
bool p3Posted::getPostRanking(const uint32_t &token, RsPostedPostRanking &ranking)
|
2012-11-30 13:54:25 -05:00
|
|
|
{
|
2012-12-11 17:26:11 -05:00
|
|
|
RsStackMutex stack(mPostedMutex);
|
|
|
|
|
|
|
|
if( mCompletePostRanks.find(token) == mCompletePostRanks.end()) return false;
|
|
|
|
|
|
|
|
ranking = mCompletePostRanks[token];
|
|
|
|
mCompletePostRanks.erase(token);
|
|
|
|
|
|
|
|
// put this in service tick as it's blocking
|
|
|
|
// and likely costly
|
|
|
|
disposeOfPublicToken(token);
|
2012-11-30 13:54:25 -05:00
|
|
|
|
2012-12-11 17:26:11 -05:00
|
|
|
return true;
|
2012-11-30 13:54:25 -05:00
|
|
|
}
|
|
|
|
|
|
|
|
void p3Posted::processRankings()
|
|
|
|
{
|
2012-12-12 17:41:21 -05:00
|
|
|
processPostRanks();
|
2012-11-30 13:54:25 -05:00
|
|
|
|
2012-12-11 17:26:11 -05:00
|
|
|
//processCommentRanks();
|
2012-11-30 13:54:25 -05:00
|
|
|
}
|
|
|
|
|
2012-12-11 17:26:11 -05:00
|
|
|
void p3Posted::processPostRanks()
|
2012-11-30 13:54:25 -05:00
|
|
|
{
|
|
|
|
|
|
|
|
RsStackMutex stack(mPostedMutex);
|
2012-12-11 17:26:11 -05:00
|
|
|
|
|
|
|
std::vector<GxsPostedPostRanking*>::iterator vit = mPendingPostRanks.begin();
|
2012-11-30 13:54:25 -05:00
|
|
|
|
2012-12-02 14:40:17 -05:00
|
|
|
// go through all pending posts
|
2012-12-12 17:41:21 -05:00
|
|
|
for(; vit !=mPendingPostRanks.end(); )
|
2012-11-30 13:54:25 -05:00
|
|
|
{
|
2012-12-11 17:26:11 -05:00
|
|
|
GxsPostedPostRanking* gp = *vit;
|
2012-11-30 13:54:25 -05:00
|
|
|
uint32_t token;
|
|
|
|
std::list<RsGxsGroupId> grpL;
|
2012-12-11 17:26:11 -05:00
|
|
|
grpL.push_back(gp->grpId);
|
|
|
|
|
2012-11-30 13:54:25 -05:00
|
|
|
RsTokReqOptions opts;
|
2012-12-11 17:26:11 -05:00
|
|
|
opts.mReqType = GXS_REQUEST_TYPE_MSG_META;
|
|
|
|
opts.mMsgFlagFilter = RsPosted::FLAG_MSGTYPE_POST;
|
|
|
|
opts.mMsgFlagMask = RsPosted::FLAG_MSGTYPE_MASK;
|
2012-11-30 13:54:25 -05:00
|
|
|
opts.mOptions = RS_TOKREQOPT_MSG_LATEST | RS_TOKREQOPT_MSG_THREAD;
|
2012-12-11 17:26:11 -05:00
|
|
|
|
2012-11-30 13:54:25 -05:00
|
|
|
RsGenExchange::getTokenService()->requestMsgInfo(token, GXS_REQUEST_TYPE_GROUP_DATA, opts, grpL);
|
2012-12-11 17:26:11 -05:00
|
|
|
|
|
|
|
|
2012-11-30 13:54:25 -05:00
|
|
|
gp->reqToken = token;
|
|
|
|
|
2012-12-11 17:26:11 -05:00
|
|
|
vit = mPendingPostRanks.erase(vit);
|
|
|
|
mCompletionPostRanks.push_back(gp);
|
|
|
|
}
|
|
|
|
|
|
|
|
mPendingPostRanks.clear();
|
|
|
|
|
|
|
|
vit = mCompletionPostRanks.begin();
|
|
|
|
|
|
|
|
for(; vit != mCompletionPostRanks.end(); )
|
|
|
|
{
|
|
|
|
bool ok = false;
|
|
|
|
GxsPostedPostRanking *gp = *vit;
|
|
|
|
uint32_t status = mTokenService->requestStatus(gp->reqToken);
|
|
|
|
|
|
|
|
if(RsTokenService::GXS_REQUEST_V2_STATUS_COMPLETE
|
|
|
|
== status)
|
2012-11-30 13:54:25 -05:00
|
|
|
{
|
2012-12-11 17:26:11 -05:00
|
|
|
ok = completePostedPostCalc(gp);
|
2012-11-30 13:54:25 -05:00
|
|
|
|
2012-12-11 17:26:11 -05:00
|
|
|
if(ok)
|
2012-11-30 13:54:25 -05:00
|
|
|
{
|
2012-12-11 17:26:11 -05:00
|
|
|
mCompletePostRanks.insert(
|
|
|
|
std::make_pair(gp->pubToken, gp->rankingResult));
|
2012-11-30 13:54:25 -05:00
|
|
|
}
|
|
|
|
}
|
2012-12-11 17:26:11 -05:00
|
|
|
else if(RsTokenService::GXS_REQUEST_V2_STATUS_FAILED
|
|
|
|
== status)
|
|
|
|
{
|
|
|
|
discardCalc(gp->reqToken);
|
|
|
|
ok = false;
|
|
|
|
}else
|
|
|
|
{
|
|
|
|
vit++;
|
|
|
|
continue;
|
|
|
|
}
|
2012-11-30 13:54:25 -05:00
|
|
|
|
2012-12-11 17:26:11 -05:00
|
|
|
if(ok)
|
|
|
|
{
|
|
|
|
updatePublicRequestStatus(gp->pubToken, RsTokenService::GXS_REQUEST_V2_STATUS_COMPLETE);
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
updatePublicRequestStatus(gp->pubToken, RsTokenService::GXS_REQUEST_V2_STATUS_FAILED);
|
|
|
|
}
|
2012-11-30 13:54:25 -05:00
|
|
|
|
2012-12-11 17:26:11 -05:00
|
|
|
vit = mCompletionPostRanks.erase(vit);
|
|
|
|
delete gp;
|
|
|
|
}
|
2012-11-30 13:54:25 -05:00
|
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
void p3Posted::discardCalc(const uint32_t &token)
|
|
|
|
{
|
2012-12-02 14:40:17 -05:00
|
|
|
mTokenService->cancelRequest(token);
|
|
|
|
}
|
|
|
|
|
|
|
|
bool PostedTopScoreComp(const PostedScore& i, const PostedScore& j)
|
|
|
|
{
|
2012-12-15 19:43:15 -05:00
|
|
|
int32_t i_score = (int32_t)i.upVotes - (int32_t)i.downVotes;
|
|
|
|
int32_t j_score = (int32_t)j.upVotes - (int32_t)j.downVotes;
|
|
|
|
|
|
|
|
if(i_score == j_score){
|
|
|
|
return i.date > j.date;
|
|
|
|
}else
|
|
|
|
{
|
|
|
|
return i_score > j_score;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
bool PostedHotScoreComp(const PostedScore& i, const PostedScore& j)
|
|
|
|
{
|
|
|
|
int32_t i_score = (int32_t)i.upVotes - (int32_t)i.downVotes;
|
|
|
|
int32_t j_score = (int32_t)j.upVotes - (int32_t)j.downVotes;
|
|
|
|
|
|
|
|
time_t now = time(NULL);
|
|
|
|
long long td = now - i.date;
|
|
|
|
|
|
|
|
if(td == 0)
|
|
|
|
{
|
|
|
|
return i.date > j.date;
|
|
|
|
}
|
|
|
|
|
|
|
|
int y;
|
|
|
|
if(i_score > 0)
|
|
|
|
{
|
|
|
|
y = 1;
|
|
|
|
}else if(i_score == 0)
|
|
|
|
{
|
|
|
|
y = 0;
|
|
|
|
}else
|
|
|
|
{
|
|
|
|
y = -1;
|
|
|
|
}
|
|
|
|
|
|
|
|
double z;
|
|
|
|
if(abs(i_score) >= 1)
|
|
|
|
{
|
|
|
|
z = abs(i_score);
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
z = 1;
|
|
|
|
}
|
|
|
|
|
|
|
|
double i_hot_score = log10(z) + ( ((double)(y*td))
|
|
|
|
/ HOT_PERIOD );
|
|
|
|
|
|
|
|
if(j_score > 0)
|
|
|
|
{
|
|
|
|
y = 1;
|
|
|
|
}else if(j_score == 0)
|
|
|
|
{
|
|
|
|
y = 0;
|
|
|
|
}else
|
|
|
|
{
|
|
|
|
y = -1;
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
if(abs(j_score) >= 1)
|
|
|
|
{
|
|
|
|
z = abs(j_score);
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
z = 1;
|
|
|
|
}
|
|
|
|
|
|
|
|
td = now - j.date;
|
|
|
|
|
|
|
|
double j_hot_score = log10(z) + ( ((double)(y*td))
|
|
|
|
/ HOT_PERIOD );
|
|
|
|
if(i_hot_score == j_hot_score)
|
|
|
|
{
|
|
|
|
return i.date > j.date;
|
|
|
|
}else
|
|
|
|
{
|
|
|
|
return i_hot_score > j_hot_score;
|
|
|
|
}
|
|
|
|
|
2012-12-02 14:40:17 -05:00
|
|
|
}
|
|
|
|
|
|
|
|
bool PostedNewScoreComp(const PostedScore& i, const PostedScore& j)
|
|
|
|
{
|
2012-12-12 17:41:21 -05:00
|
|
|
return i.date > j.date;
|
2012-12-02 14:40:17 -05:00
|
|
|
}
|
|
|
|
|
|
|
|
bool PostedBestScoreComp(const PostedScore& i, const PostedScore& j)
|
|
|
|
{
|
|
|
|
|
|
|
|
// n = ups + downs if n == 0: return 0 z = 1.0
|
|
|
|
// #1.0 = 85%, 1.6 = 95% phat = float(ups)
|
|
|
|
// / n return sqrt(phat+z*z/(2*n)-z*((phat*(1-phat)+z*z/(4*n))/n))/(1+z*z/n)
|
|
|
|
// def confidence(ups, downs): if ups + downs == 0: return 0 else:
|
|
|
|
// return _confidence(ups, downs)
|
|
|
|
// very expensive!!
|
|
|
|
|
|
|
|
static float z = 1.0;
|
|
|
|
float phat;
|
|
|
|
|
|
|
|
float i_score;
|
|
|
|
int n = i.upVotes + (-i.downVotes);
|
|
|
|
if(n==0)
|
|
|
|
i_score = 0.;
|
|
|
|
else
|
|
|
|
{
|
|
|
|
phat = float(i.upVotes);
|
|
|
|
i_score = sqrt(phat+z*z/(2*n)-z*((phat*(1-phat)+z*z/(4*n))/n))/(1+z*z/n);
|
|
|
|
}
|
|
|
|
|
|
|
|
float j_score;
|
|
|
|
n = j.upVotes + (-j.downVotes);
|
|
|
|
if(n==0)
|
|
|
|
j_score = 0.;
|
|
|
|
else
|
|
|
|
{
|
|
|
|
phat = float(j.upVotes);
|
|
|
|
j_score = sqrt(phat+z*z/(2*n)-z*((phat*(1-phat)+z*z/(4*n))/n))/(1+z*z/n);
|
|
|
|
}
|
2012-11-30 13:54:25 -05:00
|
|
|
|
2012-12-02 14:40:17 -05:00
|
|
|
if(j_score == i_score)
|
|
|
|
return i.date < j.date;
|
|
|
|
else
|
|
|
|
return i_score < j_score;
|
2012-11-30 13:54:25 -05:00
|
|
|
}
|
|
|
|
|
2012-12-11 17:26:11 -05:00
|
|
|
bool p3Posted::completePostedPostCalc(GxsPostedPostRanking *gpp)
|
2012-11-30 13:54:25 -05:00
|
|
|
{
|
|
|
|
GxsMsgMetaMap msgMetas;
|
|
|
|
|
2012-12-02 14:40:17 -05:00
|
|
|
if(getMsgMeta(gpp->reqToken, msgMetas))
|
|
|
|
{
|
2012-12-11 17:26:11 -05:00
|
|
|
std::vector<RsMsgMetaData>& msgMetaV = msgMetas[gpp->grpId];
|
2012-12-02 14:40:17 -05:00
|
|
|
switch(gpp->rType)
|
|
|
|
{
|
|
|
|
case NewRankType:
|
2012-12-11 17:26:11 -05:00
|
|
|
calcPostedPostRank(msgMetaV, gpp->rankingResult.ranking, PostedNewScoreComp);
|
2012-12-02 14:40:17 -05:00
|
|
|
break;
|
2012-12-15 19:43:15 -05:00
|
|
|
case HotRankType:
|
|
|
|
calcPostedPostRank(msgMetaV, gpp->rankingResult.ranking, PostedHotScoreComp);
|
|
|
|
break;
|
|
|
|
case TopRankType:
|
2012-12-11 17:26:11 -05:00
|
|
|
calcPostedPostRank(msgMetaV, gpp->rankingResult.ranking, PostedTopScoreComp);
|
2012-12-02 14:40:17 -05:00
|
|
|
break;
|
|
|
|
default:
|
|
|
|
std::cerr << "Unknown ranking tpye: " << gpp->rType << std::endl;
|
2013-02-07 18:04:16 -05:00
|
|
|
break;
|
2012-12-02 14:40:17 -05:00
|
|
|
}
|
2012-12-11 17:26:11 -05:00
|
|
|
return true;
|
|
|
|
}else
|
|
|
|
return false;
|
2012-12-02 14:40:17 -05:00
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
void p3Posted::calcPostedPostRank(const std::vector<RsMsgMetaData > msgMeta, PostedRanking &ranking,
|
|
|
|
bool comp(const PostedScore &, const PostedScore &)) const
|
|
|
|
{
|
|
|
|
|
|
|
|
std::vector<RsMsgMetaData>::const_iterator cit = msgMeta.begin();
|
|
|
|
std::vector<PostedScore> scores;
|
|
|
|
|
2012-12-12 17:41:21 -05:00
|
|
|
for(; cit != msgMeta.end(); cit++)
|
2012-12-02 14:40:17 -05:00
|
|
|
{
|
|
|
|
const RsMsgMetaData& m = *cit;
|
|
|
|
uint32_t upVotes, downVotes, nComments;
|
|
|
|
retrieveScores(m.mServiceString, upVotes, downVotes, nComments);
|
|
|
|
|
|
|
|
PostedScore c;
|
|
|
|
c.upVotes = upVotes;
|
|
|
|
c.downVotes = downVotes;
|
|
|
|
c.date = m.mPublishTs;
|
2012-12-12 17:41:21 -05:00
|
|
|
c.msgId = m.mMsgId;
|
2012-12-02 14:40:17 -05:00
|
|
|
scores.push_back(c);
|
|
|
|
}
|
|
|
|
|
2012-12-15 19:43:15 -05:00
|
|
|
std::sort(scores.begin(), scores.end(), comp);
|
2012-12-02 14:40:17 -05:00
|
|
|
|
|
|
|
|
2012-12-15 19:43:15 -05:00
|
|
|
for(int i = 0; i < scores.size(); i++)
|
2012-12-02 14:40:17 -05:00
|
|
|
{
|
2012-12-15 19:43:15 -05:00
|
|
|
const PostedScore& p = scores[i];
|
|
|
|
ranking.insert(std::make_pair(i+1, p.msgId));
|
2012-12-02 14:40:17 -05:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
void p3Posted::calcPostedCommentsRank(const std::map<RsGxsMessageId, std::vector<RsGxsMessageId> > &msgBranches,
|
|
|
|
std::map<RsGxsMessageId, RsMsgMetaData >& msgMetas, PostedRanking &ranking, bool comp(const PostedScore &, const PostedScore &)) const
|
|
|
|
{
|
2012-11-30 13:54:25 -05:00
|
|
|
|
2012-12-02 14:40:17 -05:00
|
|
|
std::map<RsGxsMessageId, std::vector<RsGxsMessageId> >::const_iterator cit = msgBranches.begin();
|
|
|
|
|
|
|
|
for(; cit != msgBranches.end(); cit++)
|
2012-11-30 13:54:25 -05:00
|
|
|
{
|
2012-12-02 14:40:17 -05:00
|
|
|
const std::vector<RsGxsMessageId>& branch = cit->second;
|
|
|
|
std::vector<PostedScore> scores;
|
|
|
|
|
|
|
|
std::vector<RsGxsMessageId>::const_iterator vit = branch.begin();
|
|
|
|
|
|
|
|
for(; vit != branch.end(); vit++)
|
|
|
|
{
|
|
|
|
|
|
|
|
std::map<RsGxsMessageId, RsMsgMetaData >::iterator mit =
|
|
|
|
msgMetas.find(*vit);
|
|
|
|
|
|
|
|
if(mit != msgMetas.end())
|
|
|
|
{
|
|
|
|
uint32_t upVotes, downVotes, nComments;
|
2012-11-30 13:54:25 -05:00
|
|
|
|
2012-12-02 14:40:17 -05:00
|
|
|
const RsMsgMetaData& m = mit->second;
|
|
|
|
retrieveScores(m.mServiceString, upVotes, downVotes, nComments);
|
|
|
|
|
|
|
|
PostedScore c;
|
|
|
|
c.upVotes = upVotes;
|
|
|
|
c.downVotes = downVotes;
|
|
|
|
c.date = m.mPublishTs;
|
|
|
|
scores.push_back(c);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
std::sort(scores.begin(), scores.end(), comp);
|
|
|
|
|
|
|
|
std::vector<PostedScore>::iterator cvit = scores.begin();
|
|
|
|
|
|
|
|
int i = 1;
|
|
|
|
for(; cvit != scores.end(); cvit)
|
|
|
|
{
|
|
|
|
const PostedScore& p = *cvit;
|
2012-12-11 17:26:11 -05:00
|
|
|
ranking.insert(std::make_pair(i++, p.msgId));
|
2012-12-02 14:40:17 -05:00
|
|
|
}
|
2012-11-30 13:54:25 -05:00
|
|
|
}
|
|
|
|
|
2012-12-02 14:40:17 -05:00
|
|
|
}
|
|
|
|
|
|
|
|
void p3Posted::completePostedCommentRanking(GxsPostedCommentRanking *gpc)
|
|
|
|
{
|
|
|
|
GxsMsgRelatedMetaMap msgMetas;
|
|
|
|
|
|
|
|
if(getMsgRelatedMeta(gpc->reqToken, msgMetas))
|
|
|
|
{
|
|
|
|
|
|
|
|
// create map of msgs
|
|
|
|
std::vector<RsMsgMetaData>& msgV = msgMetas[gpc->msgId];
|
|
|
|
std::map<RsGxsMessageId, std::vector<RsGxsMessageId> > msgBranches;
|
|
|
|
std::map<RsGxsMessageId, RsMsgMetaData> remappedMsgMeta;
|
|
|
|
|
|
|
|
std::vector<RsMsgMetaData>::iterator vit = msgV.begin();
|
|
|
|
|
|
|
|
for(; vit != msgV.end(); vit++)
|
|
|
|
{
|
|
|
|
const RsMsgMetaData& m = *vit;
|
|
|
|
|
|
|
|
if(!m.mParentId.empty())
|
|
|
|
{
|
|
|
|
msgBranches[m.mParentId].push_back(m.mMsgId);
|
|
|
|
}
|
|
|
|
|
|
|
|
remappedMsgMeta.insert(std::make_pair(m.mMsgId, m));
|
|
|
|
}
|
2012-11-30 13:54:25 -05:00
|
|
|
|
2012-12-02 14:40:17 -05:00
|
|
|
switch(gpc->rType)
|
|
|
|
{
|
2012-12-15 19:43:15 -05:00
|
|
|
case HotRankType:
|
2012-12-02 14:40:17 -05:00
|
|
|
calcPostedCommentsRank(msgBranches, remappedMsgMeta, gpc->result, PostedBestScoreComp);
|
|
|
|
break;
|
|
|
|
case TopRankType:
|
|
|
|
calcPostedCommentsRank(msgBranches, remappedMsgMeta, gpc->result, PostedTopScoreComp);
|
|
|
|
break;
|
|
|
|
case NewRankType:
|
|
|
|
calcPostedCommentsRank(msgBranches, remappedMsgMeta, gpc->result, PostedNewScoreComp);
|
|
|
|
break;
|
|
|
|
default:
|
|
|
|
std::cerr << "Unknown Rank type" << gpc->rType << std::endl;
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
}
|
2012-11-30 13:54:25 -05:00
|
|
|
}
|
|
|
|
|
2012-12-08 16:50:13 -05:00
|
|
|
bool p3Posted::retrieveScores(const std::string &serviceString, uint32_t &upVotes, uint32_t& downVotes, uint32_t& nComments) const
|
2012-11-30 13:54:25 -05:00
|
|
|
{
|
2012-12-02 14:40:17 -05:00
|
|
|
if (3 == sscanf(serviceString.c_str(), "%d %d %d", &upVotes, &downVotes, &nComments))
|
2012-11-30 13:54:25 -05:00
|
|
|
{
|
2012-12-02 14:40:17 -05:00
|
|
|
return true;
|
2012-11-30 13:54:25 -05:00
|
|
|
}
|
|
|
|
|
|
|
|
return false;
|
|
|
|
}
|
|
|
|
|
2012-12-02 14:40:17 -05:00
|
|
|
bool p3Posted::storeScores(std::string &serviceString, uint32_t &upVotes, uint32_t downVotes, uint32_t nComments) const
|
|
|
|
{
|
|
|
|
char line[POSTED_MAX_SERVICE_STRING];
|
|
|
|
|
|
|
|
bool ok = snprintf(line, POSTED_MAX_SERVICE_STRING, "%d %d %d", upVotes, downVotes, nComments) > -1;
|
|
|
|
|
|
|
|
serviceString = line;
|
|
|
|
return ok;
|
|
|
|
}
|
2012-11-30 13:54:25 -05:00
|
|
|
void p3Posted::processCommentRanks()
|
2012-10-05 14:12:52 -04:00
|
|
|
{
|
|
|
|
|
|
|
|
}
|
2012-12-02 14:40:17 -05:00
|
|
|
|
|
|
|
|
2012-12-08 16:50:13 -05:00
|
|
|
|
2012-12-02 14:40:17 -05:00
|
|
|
void p3Posted::updateVotes()
|
|
|
|
{
|
2012-12-08 16:50:13 -05:00
|
|
|
// any request failure stops update process
|
2012-12-02 14:40:17 -05:00
|
|
|
|
2012-12-08 16:50:13 -05:00
|
|
|
if(mPostUpdate)
|
|
|
|
{
|
2012-12-02 14:40:17 -05:00
|
|
|
switch(mUpdatePhase)
|
|
|
|
{
|
2012-12-08 16:50:13 -05:00
|
|
|
case UPDATE_PHASE_GRP_REQUEST:
|
|
|
|
{
|
|
|
|
mPostUpdate = updateRequestGroups();
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
case UPDATE_PHASE_MSG_REQUEST:
|
|
|
|
{
|
|
|
|
mPostUpdate = updateRequestMessages();
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
case UPDATE_PHASE_VOTE_COMMENT_REQUEST:
|
|
|
|
{
|
|
|
|
mPostUpdate = updateRequestVotesComments();
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
case UPDATE_PHASE_VOTE_COUNT:
|
|
|
|
{
|
|
|
|
mPostUpdate = updateCompleteVotes();
|
|
|
|
break;
|
|
|
|
}
|
2012-12-09 17:38:49 -05:00
|
|
|
case UPDATE_PHASE_COMMENT_COUNT:
|
|
|
|
{
|
|
|
|
mPostUpdate = updateCompleteComments();
|
|
|
|
break;
|
|
|
|
}
|
2012-12-08 16:50:13 -05:00
|
|
|
case UPDATE_PHASE_COMPLETE:
|
|
|
|
{
|
|
|
|
updateComplete();
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
default:
|
|
|
|
{
|
|
|
|
std::cerr << "Unknown update phase, we should not be here!" << std::endl;
|
|
|
|
break;
|
|
|
|
}
|
2012-12-02 14:40:17 -05:00
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2012-12-08 16:50:13 -05:00
|
|
|
bool p3Posted::updateRequestGroups()
|
2012-12-02 14:40:17 -05:00
|
|
|
{
|
|
|
|
|
|
|
|
|
|
|
|
RsTokReqOptions opts;
|
|
|
|
opts.mReqType = GXS_REQUEST_TYPE_GROUP_IDS;
|
2012-12-08 16:50:13 -05:00
|
|
|
// opts.mSubscribeMask = GXS_SERV::GROUP_SUBSCRIBE_MASK;
|
|
|
|
// opts.mSubscribeFilter = GXS_SERV::GROUP_SUBSCRIBE_ADMIN |
|
|
|
|
// GXS_SERV::GROUP_SUBSCRIBE_SUBSCRIBED;
|
|
|
|
mTokenService->requestGroupInfo(mUpdateRequestGroup, 0, opts);
|
2012-12-02 14:40:17 -05:00
|
|
|
|
2012-12-08 16:50:13 -05:00
|
|
|
mUpdatePhase = UPDATE_PHASE_MSG_REQUEST;
|
2013-03-01 14:01:11 -05:00
|
|
|
|
|
|
|
return true ;
|
2012-12-02 14:40:17 -05:00
|
|
|
}
|
|
|
|
|
2012-12-08 16:50:13 -05:00
|
|
|
bool p3Posted::updateRequestMessages()
|
2012-12-02 14:40:17 -05:00
|
|
|
{
|
|
|
|
|
2012-12-08 16:50:13 -05:00
|
|
|
uint32_t status = mTokenService->requestStatus(mUpdateRequestGroup);
|
2012-12-02 14:40:17 -05:00
|
|
|
|
|
|
|
if(status == RsTokenService::GXS_REQUEST_V2_STATUS_COMPLETE)
|
|
|
|
{
|
|
|
|
std::list<RsGxsGroupId> grpIds;
|
2012-12-08 16:50:13 -05:00
|
|
|
RsGenExchange::getGroupList(mUpdateRequestGroup, grpIds);
|
2012-12-02 14:40:17 -05:00
|
|
|
RsTokReqOptions opts;
|
2012-12-08 16:50:13 -05:00
|
|
|
opts.mReqType = GXS_REQUEST_TYPE_MSG_META;
|
2012-12-02 14:40:17 -05:00
|
|
|
opts.mOptions = RS_TOKREQOPT_MSG_LATEST | RS_TOKREQOPT_MSG_THREAD;
|
2012-12-08 16:50:13 -05:00
|
|
|
mTokenService->requestMsgInfo(mUpdateRequestMessages, 0, opts, grpIds);
|
|
|
|
mUpdatePhase = UPDATE_PHASE_VOTE_COMMENT_REQUEST;
|
2012-12-02 14:40:17 -05:00
|
|
|
return true;
|
|
|
|
}
|
|
|
|
else if(status == RsTokenService::GXS_REQUEST_V2_STATUS_FAILED)
|
|
|
|
{
|
2012-12-08 16:50:13 -05:00
|
|
|
mTokenService->cancelRequest(mUpdateRequestGroup);
|
2012-12-02 14:40:17 -05:00
|
|
|
return false;
|
|
|
|
}
|
2012-12-08 16:50:13 -05:00
|
|
|
|
|
|
|
return true;
|
2012-12-02 14:40:17 -05:00
|
|
|
}
|
|
|
|
|
2012-12-08 16:50:13 -05:00
|
|
|
bool p3Posted::updateRequestVotesComments()
|
2012-12-02 14:40:17 -05:00
|
|
|
{
|
|
|
|
|
2012-12-08 16:50:13 -05:00
|
|
|
uint32_t status = mTokenService->requestStatus(mUpdateRequestMessages);
|
2012-12-02 14:40:17 -05:00
|
|
|
|
|
|
|
if(status == RsTokenService::GXS_REQUEST_V2_STATUS_COMPLETE)
|
|
|
|
{
|
|
|
|
|
2012-12-08 16:50:13 -05:00
|
|
|
RsGenExchange::getMsgMeta(mUpdateRequestMessages, mMsgMetaUpdate);
|
2012-12-02 14:40:17 -05:00
|
|
|
|
|
|
|
std::vector<RsGxsGrpMsgIdPair> msgIds;
|
|
|
|
|
2012-12-08 16:50:13 -05:00
|
|
|
GxsMsgMetaMap::iterator mit = mMsgMetaUpdate.begin();
|
2012-12-02 14:40:17 -05:00
|
|
|
|
2012-12-08 16:50:13 -05:00
|
|
|
for(; mit != mMsgMetaUpdate.end(); mit++)
|
2012-12-02 14:40:17 -05:00
|
|
|
{
|
2012-12-08 16:50:13 -05:00
|
|
|
std::vector<RsMsgMetaData>& msgIdV = mit->second;
|
|
|
|
std::vector<RsMsgMetaData>::const_iterator cit = msgIdV.begin();
|
2012-12-02 14:40:17 -05:00
|
|
|
|
|
|
|
for(; cit != msgIdV.end(); cit++)
|
2012-12-08 16:50:13 -05:00
|
|
|
msgIds.push_back(std::make_pair(mit->first, cit->mMsgId));
|
2012-12-02 14:40:17 -05:00
|
|
|
}
|
|
|
|
|
|
|
|
RsTokReqOptions opts;
|
2012-12-09 17:38:49 -05:00
|
|
|
// only need ids for comments
|
|
|
|
|
|
|
|
opts.mReqType = GXS_REQUEST_TYPE_MSG_RELATED_IDS;
|
|
|
|
opts.mOptions = RS_TOKREQOPT_MSG_LATEST | RS_TOKREQOPT_MSG_PARENT;
|
|
|
|
opts.mMsgFlagMask = RsPosted::FLAG_MSGTYPE_MASK;
|
|
|
|
opts.mMsgFlagFilter = RsPosted::FLAG_MSGTYPE_COMMENT;
|
|
|
|
mTokenService->requestMsgRelatedInfo(mUpdateRequestComments, 0, opts, msgIds);
|
2012-12-08 16:50:13 -05:00
|
|
|
|
|
|
|
// need actual data for votes
|
|
|
|
opts.mReqType = GXS_REQUEST_TYPE_MSG_RELATED_DATA;
|
2012-12-02 14:40:17 -05:00
|
|
|
opts.mOptions = RS_TOKREQOPT_MSG_LATEST | RS_TOKREQOPT_MSG_PARENT;
|
|
|
|
opts.mMsgFlagMask = RsPosted::FLAG_MSGTYPE_MASK;
|
|
|
|
opts.mMsgFlagFilter = RsPosted::FLAG_MSGTYPE_VOTE;
|
2012-12-08 16:50:13 -05:00
|
|
|
mTokenService->requestMsgRelatedInfo(mUpdateRequestVotes, 0, opts, msgIds);
|
2012-12-02 14:40:17 -05:00
|
|
|
|
2012-12-08 16:50:13 -05:00
|
|
|
mUpdatePhase = UPDATE_PHASE_VOTE_COUNT;
|
2012-12-02 14:40:17 -05:00
|
|
|
|
|
|
|
return true;
|
|
|
|
}
|
|
|
|
else if(status == RsTokenService::GXS_REQUEST_V2_STATUS_FAILED)
|
|
|
|
{
|
2012-12-08 16:50:13 -05:00
|
|
|
mTokenService->cancelRequest(mUpdateRequestMessages);
|
2012-12-02 14:40:17 -05:00
|
|
|
return false;
|
|
|
|
}
|
|
|
|
|
2012-12-08 16:50:13 -05:00
|
|
|
return true;
|
|
|
|
}
|
2012-12-02 14:40:17 -05:00
|
|
|
|
|
|
|
|
2012-12-08 16:50:13 -05:00
|
|
|
bool p3Posted::updateCompleteVotes()
|
|
|
|
{
|
|
|
|
uint32_t status = mTokenService->requestStatus(mUpdateRequestVotes);
|
2012-12-02 14:40:17 -05:00
|
|
|
|
2012-12-08 16:50:13 -05:00
|
|
|
if(status == RsTokenService::GXS_REQUEST_V2_STATUS_COMPLETE)
|
2012-12-02 14:40:17 -05:00
|
|
|
{
|
|
|
|
std::map<RsGxsGrpMsgIdPair, std::vector<RsPostedVote> > votes;
|
2012-12-08 16:50:13 -05:00
|
|
|
getMsgRelatedDataT<RsGxsPostedVoteItem, RsPostedVote>(mUpdateRequestVotes,
|
|
|
|
votes);
|
|
|
|
|
|
|
|
// now for each msg count the number of votes and thats it
|
2012-12-02 14:40:17 -05:00
|
|
|
|
2012-12-08 16:50:13 -05:00
|
|
|
std::map<RsGxsGrpMsgIdPair, std::vector<RsPostedVote> >::iterator mit = votes.begin();
|
|
|
|
|
|
|
|
for(; mit != votes.end(); mit++)
|
2012-12-02 14:40:17 -05:00
|
|
|
{
|
2012-12-08 16:50:13 -05:00
|
|
|
const std::vector<RsPostedVote>& v = mit->second;
|
|
|
|
std::vector<RsPostedVote>::const_iterator cit = v.begin();
|
|
|
|
|
|
|
|
for(; cit != v.end(); cit++)
|
|
|
|
{
|
|
|
|
const RsPostedVote& vote = *cit;
|
|
|
|
|
|
|
|
if(vote.mDirection)
|
|
|
|
{
|
|
|
|
mMsgCounts[mit->first].upVotes++;
|
|
|
|
}else
|
|
|
|
{
|
|
|
|
mMsgCounts[mit->first].downVotes++;
|
|
|
|
}
|
|
|
|
}
|
2012-12-02 14:40:17 -05:00
|
|
|
}
|
2012-12-09 17:38:49 -05:00
|
|
|
mUpdatePhase = UPDATE_PHASE_COMMENT_COUNT;
|
2012-12-02 14:40:17 -05:00
|
|
|
}
|
2012-12-08 16:50:13 -05:00
|
|
|
else if(status == RsTokenService::GXS_REQUEST_V2_STATUS_FAILED)
|
2012-12-02 14:40:17 -05:00
|
|
|
{
|
2012-12-08 16:50:13 -05:00
|
|
|
mTokenService->cancelRequest(mUpdateRequestVotes);
|
2012-12-02 14:40:17 -05:00
|
|
|
return false;
|
|
|
|
}
|
2012-12-08 16:50:13 -05:00
|
|
|
return true;
|
2012-12-02 14:40:17 -05:00
|
|
|
}
|
|
|
|
|
2012-12-09 17:38:49 -05:00
|
|
|
bool p3Posted::updateCompleteComments()
|
|
|
|
{
|
|
|
|
uint32_t status = mTokenService->requestStatus(mUpdateRequestComments);
|
|
|
|
|
|
|
|
if(status == RsTokenService::GXS_REQUEST_V2_STATUS_COMPLETE)
|
|
|
|
{
|
|
|
|
MsgRelatedIdResult commentIds;
|
|
|
|
RsGenExchange::getMsgRelatedList(mUpdateRequestComments, commentIds);
|
|
|
|
|
|
|
|
// now for each msg count the number of votes and thats it
|
|
|
|
|
|
|
|
MsgRelatedIdResult::iterator mit = commentIds.begin();
|
|
|
|
|
|
|
|
for(; mit != commentIds.end(); mit++)
|
|
|
|
{
|
|
|
|
const std::vector<RsGxsMessageId>& v = mit->second;
|
|
|
|
std::vector<RsGxsMessageId>::const_iterator cit = v.begin();
|
|
|
|
|
|
|
|
for(; cit != v.end(); cit++)
|
|
|
|
{
|
|
|
|
mMsgCounts[mit->first].commentCount++;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
mUpdatePhase = UPDATE_PHASE_COMPLETE;
|
|
|
|
}
|
|
|
|
else if(status == RsTokenService::GXS_REQUEST_V2_STATUS_FAILED)
|
|
|
|
{
|
|
|
|
mTokenService->cancelRequest(mUpdateRequestComments);
|
|
|
|
return false;
|
|
|
|
}
|
|
|
|
return true;
|
|
|
|
}
|
|
|
|
|
2012-12-08 16:50:13 -05:00
|
|
|
bool p3Posted::updateComplete()
|
2012-12-02 14:40:17 -05:00
|
|
|
{
|
2012-12-08 16:50:13 -05:00
|
|
|
// now compare with msg meta to see what currently store there
|
2012-12-02 14:40:17 -05:00
|
|
|
|
2012-12-08 16:50:13 -05:00
|
|
|
GxsMsgMetaMap::iterator mit = mMsgMetaUpdate.begin();
|
2012-12-02 14:40:17 -05:00
|
|
|
|
2012-12-08 16:50:13 -05:00
|
|
|
for(; mit != mMsgMetaUpdate.end(); mit++)
|
2012-12-02 14:40:17 -05:00
|
|
|
{
|
2012-12-08 16:50:13 -05:00
|
|
|
const std::vector<RsMsgMetaData>& msgMetaV = mit->second;
|
|
|
|
std::vector<RsMsgMetaData>::const_iterator cit = msgMetaV.begin();
|
2012-12-02 14:40:17 -05:00
|
|
|
|
2012-12-08 16:50:13 -05:00
|
|
|
for(; cit != msgMetaV.end(); cit++)
|
2012-12-02 14:40:17 -05:00
|
|
|
{
|
2012-12-08 16:50:13 -05:00
|
|
|
const RsMsgMetaData& msgMeta = *cit;
|
|
|
|
uint32_t upVotes, downVotes, nComments;
|
|
|
|
retrieveScores(msgMeta.mServiceString, upVotes, downVotes, nComments);
|
|
|
|
|
|
|
|
RsGxsGrpMsgIdPair msgId;
|
|
|
|
msgId.first = mit->first;
|
|
|
|
msgId.second = msgMeta.mMsgId;
|
|
|
|
PostedScore& sc = mMsgCounts[msgId];
|
|
|
|
|
2012-12-09 17:38:49 -05:00
|
|
|
bool changed = (sc.upVotes != upVotes) || (sc.downVotes != downVotes)
|
|
|
|
|| (sc.commentCount != nComments);
|
2012-12-08 16:50:13 -05:00
|
|
|
|
|
|
|
if(changed)
|
|
|
|
{
|
|
|
|
std::string servStr;
|
2012-12-09 17:38:49 -05:00
|
|
|
storeScores(servStr, sc.upVotes, sc.downVotes, sc.commentCount);
|
2012-12-08 16:50:13 -05:00
|
|
|
uint32_t token;
|
|
|
|
setMsgServiceString(token, msgId, servStr);
|
|
|
|
mChangeTokens.push_back(token);
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
mMsgCounts.erase(msgId);
|
|
|
|
}
|
2012-12-02 14:40:17 -05:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2012-12-08 16:50:13 -05:00
|
|
|
mPostUpdate = false;
|
|
|
|
mUpdatePhase = UPDATE_PHASE_GRP_REQUEST;
|
2012-12-09 17:38:49 -05:00
|
|
|
|
|
|
|
if(!mMsgCounts.empty())
|
|
|
|
{
|
|
|
|
RsGxsMsgChange* msgChange = new RsGxsMsgChange();
|
|
|
|
|
|
|
|
std::map<RsGxsGrpMsgIdPair, PostedScore >::iterator mit_c = mMsgCounts.begin();
|
|
|
|
|
|
|
|
for(; mit_c != mMsgCounts.end(); mit_c++)
|
|
|
|
{
|
|
|
|
const RsGxsGrpMsgIdPair& msgId = mit_c->first;
|
|
|
|
msgChange->msgChangeMap[msgId.first].push_back(msgId.second);
|
|
|
|
}
|
|
|
|
|
|
|
|
std::vector<RsGxsNotify*> n;
|
|
|
|
n.push_back(msgChange);
|
|
|
|
notifyChanges(n);
|
|
|
|
|
|
|
|
mMsgCounts.clear();
|
|
|
|
}
|
|
|
|
|
2013-03-01 14:01:11 -05:00
|
|
|
|
|
|
|
return true ;
|
2012-12-08 16:50:13 -05:00
|
|
|
}
|