summaryrefslogtreecommitdiff
path: root/client/DownloadClient.cpp
blob: 723dbcbd3fefebbf203335dcd3de864215dbae40 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118

#include <QtCore>
#include "DownloadClient.h"
#include "Utility.h"


DownloadClient::DownloadClient(): isDownloading(false), current(NULL), currentId(-1)
{
}

DownloadClient::DownloadClient(QString addr): SslClient(addr), isDownloading(false), current(NULL), currentId(-1)
{
}

void DownloadClient::Download(const string &filename)
{
	pair<string, string> file(filename, 0);
	vector<pair<string, string> > fileList;
	fileList.push_back(file);
	Download(fileList);		
}

void DownloadClient::Download(const pair<string, string> &file)
{
	vector<pair<string, string> > fileList;
	fileList.push_back(file);
	Download(fileList);	
}

void DownloadClient::Download(const vector<pair<string, string> > &fileList)
{
	if (server.isEmpty())
	{
		Logger::Error("Server address isn't set! Aborting.\n");
		return;
	}
	if (isDownloading)
	{
		Logger::Error("Previous downloading process wasn't finished! Aborting.\n");
		return;
	}
	
	connect(this, SIGNAL(ReplyRecieved(SslClient::RequestType&, QByteArray&)),
		this, SLOT(FileDataRecieved(SslClient::RequestType&, QByteArray&)));
	isDownloading = true;
	files = fileList;
	DoDownload();
}

void DownloadClient::DoDownload()
{
	currentId++;
	
	if (currentId < (int)files.size())
	{
		pair<string, string> file = files[currentId];
		QString filename = QString::fromLocal8Bit(file.first.c_str());		
		string md5 = file.second;
		current = new QFile(filename);
		current->open(QIODevice::WriteOnly | QIODevice::Unbuffered);

		Logger::Info("Downloading file (%d of %u): %s\n", currentId + 1, files.size(), file.first.c_str());
		SendFileRequest(file.first);
	}
	else
	{
		Logger::Info("All files have been downloaded.\n");
		isDownloading = false;
		emit downloadFinished();
	}
}

void DownloadClient::FileDataRecieved(SslClient::RequestType &type, QByteArray &data)
{
	Logger::Trace("Recieved file data: %u bytes\n", data.size());
	if (type != RegularFile)
	{
		Logger::Error("Invalid reply recieved: %x\n", type);
		return;
	}
	if ((current == NULL) || (! current->isOpen()))
	{
		Logger::Error("File isn't open or in invalid state.\n");
		return;
	}
	
	if (data.size() != 0)
	{
		current->write(data);
		current->waitForBytesWritten(-1);
	}
	else
	{
		Logger::Trace("Last (empty) packet recieved\n");
		current->close();
		
		// check file's md5 hash value
		pair<string, string> file = files[currentId];
		QString md5string = QString::fromLocal8Bit(file.second.c_str());
		QString filename = QString::fromLocal8Bit(file.first.c_str());
		QByteArray md5 = md5_sum(filename);
		if (md5 == md5string)
		{
			Logger::Trace("File %s was downloaded correctly!\n", filename.toStdString().c_str());
		}
		else
		{
			Logger::Error("File %s was downloaded incorrectly! Removing and trying again!\n", filename.toStdString().c_str());
			current->remove();
			currentId--;
		}
		// free pointer to the current file
		delete current;
		current = NULL;
		// proceed to the next file
		DoDownload();
	}
}