From a154027918d0a5f2f270615e606d463e35a80d1e Mon Sep 17 00:00:00 2001 From: Alexander Lantsev Date: Tue, 18 Feb 2014 18:25:28 +0000 Subject: added file transfer visualisation added message with file download link cleaned project and code git-svn-id: http://svn.miranda-ng.org/main/trunk@8164 1316c22d-e87f-b044-9b9b-93d7a3e3ba9c --- plugins/DropBox/DropBox_11.vcxproj | 12 +-- plugins/DropBox/src/dropBox_proto.cpp | 165 ++++++++++++++++++++++------------ plugins/DropBox/src/dropBox_proto.h | 42 +++++++-- plugins/DropBox/src/main.cpp | 1 - 4 files changed, 151 insertions(+), 69 deletions(-) (limited to 'plugins/DropBox') diff --git a/plugins/DropBox/DropBox_11.vcxproj b/plugins/DropBox/DropBox_11.vcxproj index e0ae749cf7..e71e63d967 100644 --- a/plugins/DropBox/DropBox_11.vcxproj +++ b/plugins/DropBox/DropBox_11.vcxproj @@ -130,8 +130,8 @@ 4996;%(DisableSpecificWarnings) MultiThreadedDebugDLL $(IntDir)\%(RelativeDir)\ - Use - Steam.h + NotUsing + common.h Windows @@ -157,8 +157,8 @@ ..\..\include;..\..\plugins\ExternalAPI;%(AdditionalIncludeDirectories) 4996;%(DisableSpecificWarnings) $(IntDir)\%(RelativeDir)\ - Use - Steam.h + NotUsing + common.h Windows @@ -185,8 +185,8 @@ ..\..\include;..\..\plugins\ExternalAPI;%(AdditionalIncludeDirectories) 4996;%(DisableSpecificWarnings) $(IntDir)\%(RelativeDir)\ - Use - Steam.h + NotUsing + common.h Windows diff --git a/plugins/DropBox/src/dropBox_proto.cpp b/plugins/DropBox/src/dropBox_proto.cpp index f1991a9924..a9b9d08edb 100644 --- a/plugins/DropBox/src/dropBox_proto.cpp +++ b/plugins/DropBox/src/dropBox_proto.cpp @@ -3,6 +3,11 @@ HANDLE g_hNetlibUser; ULONG g_fileId = 1; +bool HasAccessToken() +{ + return db_get_sa(NULL, MODULE, "TokenSecret") != NULL; +} + int OnModulesLoaded(WPARAM wParam, LPARAM lParam) { NETLIBUSER nlu = { sizeof(nlu) }; @@ -57,7 +62,7 @@ HttpRequest *DropBoxCreateFileChunkedRequest(const char *data, int length) request->AddParameter("access_token", db_get_sa(NULL, MODULE, "TokenSecret")); if (length > 0) { - //request->AddHeader("Content-Type", "application/octet-stream"); + request->AddHeader("Content-Type", "application/octet-stream"); request->dataLength = length; request->pData = (char*)mir_alloc(sizeof(char) * (length + 1)); memcpy(request->pData, data, length); @@ -123,8 +128,9 @@ bool DropBoxSendFileChunkedEnd(const char *fileName, const char *uploadId, MCONT mir_snprintf( url, SIZEOF(url), - "%s/commit_chunked_upload/sandbox/%s", + "%s/commit_chunked_upload/%s/%s", DROPBOX_APICONTENT_URL, + DROPBOX_API_ROOT, fileName); HttpRequest *request = new HttpRequest(g_hNetlibUser, REQUEST_POST, url); @@ -137,20 +143,37 @@ bool DropBoxSendFileChunkedEnd(const char *fileName, const char *uploadId, MCONT if (response && response->resultCode == 200) { - //char message[MAX_PATH]; - //mir_snprintf( - // message, - // SIZEOF(message), - // "%s/files/sandbox/%s", - // DROPBOX_APICONTENT_URL, - // fileName); - - //PROTORECVEVENT recv = { 0 }; - ////recv.flags = flags; - ////recv.lParam = (LPARAM)¶m; - //recv.timestamp = time(NULL); - //recv.szMessage = ::mir_strdup(message); - //::ProtoChainRecvMsg(hContact, &recv); + mir_snprintf( + url, + SIZEOF(url), + "%s/shares/%s/%s", + DROPBOX_API_URL, + DROPBOX_API_ROOT, + fileName); + + request = new HttpRequest(g_hNetlibUser, REQUEST_POST, url); + request->AddParameter("access_token", db_get_sa(NULL, MODULE, "TokenSecret")); + + response = request->Send(); + + if (response && response->resultCode == 200) + { + JSONNODE *root = json_parse(response->pData); + if (root != NULL) + { + JSONNODE *node = json_get(root, "url"); + char *message = mir_utf8encodeW(json_as_string(node)); + + DBEVENTINFO dbei = { sizeof(dbei) }; + dbei.szModule = MODULE; + dbei.timestamp = time(NULL); + dbei.eventType = EVENTTYPE_MESSAGE; + dbei.cbBlob = strlen(message); + dbei.pBlob = (PBYTE)mir_strdup(message); + dbei.flags = DBEF_UTF; + ::db_event_add(hContact, &dbei); + } + } return true; } @@ -158,76 +181,106 @@ bool DropBoxSendFileChunkedEnd(const char *fileName, const char *uploadId, MCONT return false; } -void DropBoxAsyncFileSend(void *args) +void DropBoxAsyncFileSend(void *arg) { -} + FileTransferParam *ftp = (FileTransferParam *)arg; -INT_PTR DropBoxSendFile(WPARAM wParam, LPARAM lParam) -{ - CCSDATA *pccsd=(CCSDATA*)lParam; + ProtoBroadcastAck(MODULE, ftp->pfts.hContact, ACKTYPE_FILE, ACKRESULT_INITIALISING, ftp->hProcess, 0); - char **files = (char**)pccsd->lParam; - for (int i = 0; files[i]; i++) + for (int i = 0; ftp->pfts.pszFiles[i]; i++) { - FILE *file = fopen(files[i], "rb"); + FILE *file = fopen(ftp->pfts.pszFiles[i], "rb"); if (file != NULL) { int offset = 0; - bool isFirstChunk = true; char *uploadId = new char[32]; - const char *fileName = strrchr(files[i], '\\') + 1; + const char *fileName = strrchr(ftp->pfts.pszFiles[i], '\\') + 1; + + fseek(file, 0, SEEK_END); + DWORD fileSize = ftell(file); + fseek(file, 0, SEEK_SET); + + ftp->pfts.currentFileNumber = i; + ftp->pfts.currentFileSize = fileSize; + ftp->pfts.currentFileProgress = 0; + ftp->pfts.szCurrentFile = strrchr(ftp->pfts.pszFiles[i], '\\') + 1; + + ProtoBroadcastAck(MODULE, ftp->pfts.hContact, ACKTYPE_FILE, ACKRESULT_DATA, ftp->hProcess, (LPARAM)&ftp->pfts); while (!feof(file) && !ferror(file)) { - char *data = new char[DROPBOX_FILE_CHUNK_SIZE + 1]; - size_t count = fread(data, sizeof(char), DROPBOX_FILE_CHUNK_SIZE, file); + int chunkSize = DROPBOX_FILE_CHUNK_SIZE; + if (fileSize < 1024*1024) + chunkSize = DROPBOX_FILE_CHUNK_SIZE / 5; + else if (fileSize > 20*1024*1024) + chunkSize = DROPBOX_FILE_CHUNK_SIZE * 4; - if (isFirstChunk) - { + char *data = new char[chunkSize + 1]; + size_t count = fread(data, sizeof(char), chunkSize, file); + + if (!offset) DropBoxSendFileChunkedStart(data, count, uploadId, offset); - isFirstChunk = false; - } else - { DropBoxSendFileChunkedNext(data, count, uploadId, offset); - } + + ftp->pfts.currentFileProgress += count; + ftp->pfts.totalProgress += count; + + ProtoBroadcastAck(MODULE, ftp->pfts.hContact, ACKTYPE_FILE, ACKRESULT_DATA, ftp->hProcess, (LPARAM)&ftp->pfts); } fclose(file); - return DropBoxSendFileChunkedEnd(fileName, uploadId, pccsd->hContact); + DropBoxSendFileChunkedEnd(fileName, uploadId, ftp->pfts.hContact); + ftp->pfts.currentFileProgress = ftp->pfts.currentFileSize; + if (i < ftp->pfts.totalFiles - 1) + ProtoBroadcastAck(MODULE, ftp->pfts.hContact, ACKTYPE_FILE, ACKRESULT_NEXTFILE, ftp->hProcess, 0); } - - //ULONG fileId = ::InterlockedIncrement(&g_fileId); - - //return fileId; } - return 0; + ProtoBroadcastAck(MODULE, ftp->pfts.hContact, ACKTYPE_FILE, ACKRESULT_SUCCESS, ftp->hProcess, 0); + + delete ftp; } -INT_PTR DropBoxSendMessage(WPARAM wParam, LPARAM lParam) +INT_PTR DropBoxSendFile(WPARAM wParam, LPARAM lParam) { - return 0; + CCSDATA *pccsd = (CCSDATA*)lParam; + + FileTransferParam *ftp = new FileTransferParam(); + ftp->pfts.flags = PFTS_SENDING | PFTS_UTF; + ftp->pfts.hContact = pccsd->hContact; + + char **files = (char**)pccsd->lParam; + + for (ftp->pfts.totalFiles = 0; files[ftp->pfts.totalFiles]; ftp->pfts.totalFiles++); + ftp->pfts.pszFiles = new char*[ftp->pfts.totalFiles + 1]; + ftp->pfts.pszFiles[ftp->pfts.totalFiles] = NULL; + for (int i = 0; i < ftp->pfts.totalFiles; i++) + { + ftp->pfts.pszFiles[i] = mir_strdup(files[i]); + + FILE *file = fopen(files[i], "rb"); + if (file != NULL) + { + fseek(file, 0, SEEK_END); + ftp->pfts.totalBytes += ftell(file); + fseek(file, 0, SEEK_SET); + fclose(file); + } + } + ULONG fileId = ::InterlockedIncrement(&g_fileId); + ftp->hProcess = (HANDLE)fileId; + + mir_forkthread(DropBoxAsyncFileSend, ftp); + + return fileId; } -INT_PTR DropBoxReceiveMessage(WPARAM wParam, LPARAM lParam) +INT_PTR DropBoxSendMessage(WPARAM wParam, LPARAM lParam) { - /*CCSDATA *pccsd = (CCSDATA *)lParam; - PROTORECVEVENT *ppre = (PROTORECVEVENT *)pccsd->lParam; - return CallService(MS_PROTO_CHAINRECV, wParam, lParam); - - DBEVENTINFO dbei = { sizeof(dbei) }; - dbei.szModule = MODULE; - dbei.timestamp = ppre->timestamp; - dbei.eventType = type; - dbei.cbBlob = ppre->cbCustomDataSize; - dbei.pBlob = ppre->szMessage; - dbei.flags = flags; - return ::db_event_add(pccsd->hContact, &dbei);*/ - return 0; } diff --git a/plugins/DropBox/src/dropBox_proto.h b/plugins/DropBox/src/dropBox_proto.h index 2127755059..b79f405fdc 100644 --- a/plugins/DropBox/src/dropBox_proto.h +++ b/plugins/DropBox/src/dropBox_proto.h @@ -5,18 +5,49 @@ #include "http_request.h" #define DROPBOX_API_VER "1" - +#define DROPBOX_API_ROOT "sandbox" #define DROPBOX_API_URL "https://api.dropbox.com/" DROPBOX_API_VER #define DROPBOX_APICONTENT_URL "https://api-content.dropbox.com/" DROPBOX_API_VER #define DROPBOX_API_KEY "fa8du7gkf2q8xzg" -#include "..\..\DropBoxApi\sekret_key.h" +#include "..\..\DropBox\secret_key.h" -#define DROPBOX_FILE_CHUNK_SIZE 100 * 1024 //100 KB -//4 * 1024 * 1024 // 4 MB +#define DROPBOX_FILE_CHUNK_SIZE 1024 * 1024 //1 MB extern ULONG g_fileId; +struct FileTransferParam +{ + HANDLE hProcess; + PROTOFILETRANSFERSTATUS pfts; + + FileTransferParam() + { + pfts.cbSize = sizeof(this->pfts); + pfts.flags = PFTS_UTF; + pfts.currentFileNumber = 0; + pfts.currentFileProgress = 0; + pfts.currentFileSize = 0; + pfts.currentFileTime = 0; + pfts.totalBytes = 0; + pfts.totalFiles = 0; + pfts.totalProgress = 0; + pfts.tszWorkingDir = NULL; + pfts.wszCurrentFile = NULL; + } + + ~FileTransferParam() + { + for (int i = 0; pfts.pszFiles[pfts.totalFiles]; i++) + { + delete pfts.pszFiles[i]; + } + delete pfts.pszFiles; + } +}; + +bool HasAccessToken(); + void SetContactStatus(MCONTACT hContact, int newStatus); bool DropBoxLogIn(); @@ -26,14 +57,13 @@ int OnModulesLoaded(WPARAM wParam, LPARAM lParam); INT_PTR DropBoxGetCaps(WPARAM wParam, LPARAM lParam); INT_PTR DropBoxSendMessage(WPARAM wParam, LPARAM lParam); -INT_PTR DropBoxReceiveMessage(WPARAM wParam, LPARAM lParam); HttpRequest *DropBoxCreateFileChunkedRequest(const char *data, int length); bool DropBoxSendFileChunkedStart(const char *data, int length, char *uploadId, int &offset); bool DropBoxSendFileChunkedNext(const char *data, int length, const char *uploadId, int &offset); bool DropBoxSendFileChunkedEnd(const char *fileName, const char *uploadId, MCONTACT hContact); -void DropBoxAsyncFileSend(void *args); +void DropBoxAsyncFileSend(void *arg); INT_PTR DropBoxSendFile(WPARAM wParam, LPARAM lParam); diff --git a/plugins/DropBox/src/main.cpp b/plugins/DropBox/src/main.cpp index a4e97b0a24..79a826f042 100644 --- a/plugins/DropBox/src/main.cpp +++ b/plugins/DropBox/src/main.cpp @@ -52,7 +52,6 @@ extern "C" int __declspec(dllexport) Load(void) CreateProtoServiceFunction(MODULE, PSS_FILE, DropBoxSendFile); CreateProtoServiceFunction(MODULE, PSS_MESSAGE, DropBoxSendMessage); - CreateProtoServiceFunction(MODULE, PSR_MESSAGE, DropBoxReceiveMessage); return 0; } -- cgit v1.2.3