summaryrefslogtreecommitdiffstats
path: root/src/gui/serverFileTransfert.cpp
diff options
context:
space:
mode:
authorSebastian2010-05-12 19:42:27 +0200
committerSebastian2010-05-12 19:42:27 +0200
commitce3329047d378a14006ce74ec273ac59e3375303 (patch)
tree782430f270b4c7aca1b35d5b7813518e3797c555 /src/gui/serverFileTransfert.cpp
downloadpvs-ce3329047d378a14006ce74ec273ac59e3375303.tar.gz
pvs-ce3329047d378a14006ce74ec273ac59e3375303.tar.xz
pvs-ce3329047d378a14006ce74ec273ac59e3375303.zip
initial import of latest svn version
Diffstat (limited to 'src/gui/serverFileTransfert.cpp')
-rw-r--r--src/gui/serverFileTransfert.cpp265
1 files changed, 265 insertions, 0 deletions
diff --git a/src/gui/serverFileTransfert.cpp b/src/gui/serverFileTransfert.cpp
new file mode 100644
index 0000000..22e268b
--- /dev/null
+++ b/src/gui/serverFileTransfert.cpp
@@ -0,0 +1,265 @@
+/*
+# Copyright (c) 2009 - OpenSLX Project, Computer Center University of Freiburg
+#
+# This program is free software distributed under the GPL version 2.
+# See http://openslx.org/COPYING
+#
+# If you have any feedback please consult http://openslx.org/feedback and
+# send your suggestions, praise, or complaints to feedback@openslx.org
+#
+# General information about OpenSLX can be found at http://openslx.org/
+# -----------------------------------------------------------------------------
+# src/gui/serverFileTransfert.cpp
+# This class manage any file transfert from and to server.
+# -----------------------------------------------------------------------------
+*/
+
+#include "serverFileTransfert.h"
+
+ServerFileTransfert::ServerFileTransfert(QWidget *parent):
+ QDialog(parent)
+{
+ setupUi(this);
+ _file = NULL;
+ _socket = NULL;
+
+ connect(this, SIGNAL(finished(int)), this, SLOT(deleteLater()));
+}
+
+ServerFileTransfert::~ServerFileTransfert()
+{
+}
+
+void ServerFileTransfert::sendFileToHost(QString host)
+{
+ QString filename = QFileDialog::getOpenFileName(this, tr("Open File"),
+ QDir::homePath(), "");
+ if (filename == "")
+ {
+ reject();
+ return;
+ }
+ sendFileToHost(host, filename);
+}
+
+void ServerFileTransfert::sendFileToHost(QString host, QString filename)
+{
+ // open file
+ _file = new QFile(filename);
+ _file->open(QIODevice::ReadOnly);
+ _bytesToWrite = _file->size();
+ div = 1 + _bytesToWrite / 1000000000; // bc. progressBar supports only int
+
+ // get host from backend
+
+ // gui
+ filenameLabel->setText(filename);
+ progressBar->setValue(0);
+ progressBar->setMaximum(_bytesToWrite/div);
+ labelB->setText(formatSize(_bytesToWrite));
+ connect(cancelButton, SIGNAL(clicked()), this, SLOT(close()));
+
+ // open socket
+ _socket = new QTcpSocket();
+ _socket->connectToHost(host, 29481);
+ if (_socket->isOpen())
+ qDebug("connection open");
+ else
+ qDebug("connection closed");
+ qDebug("[%s] Remote host: %s", metaObject()->className(), qPrintable(host));
+
+ connect(_socket, SIGNAL(connected()), this, SLOT(sendHeader()));
+ connect(_socket, SIGNAL(disconnected()), this, SLOT(close()));
+ connect(_socket, SIGNAL(error(QAbstractSocket::SocketError)),
+ this, SLOT(error(QAbstractSocket::SocketError)));
+ qDebug("connect is set");
+}
+
+void ServerFileTransfert::receiveFileFromHost(QTcpSocket* socket)
+{
+
+ _bytesToRead = 0;
+ _socket = socket;
+
+ connect(_socket, SIGNAL(readyRead()), this, SLOT(receiveHeader()));
+ connect(_socket, SIGNAL(disconnected()), this, SLOT(close()));
+ connect(_socket, SIGNAL(error(QAbstractSocket::SocketError)),
+ this, SLOT(error(QAbstractSocket::SocketError)));
+
+ qDebug("[%s] New Connection: %s", metaObject()->className(),
+ qPrintable(_socket->peerAddress().toString()));
+}
+
+void ServerFileTransfert::sendHeader()
+{
+ qDebug("[%s] Sending header(1)...", metaObject()->className());
+ QFileInfo info(_file->fileName());
+ QString size = QString::number(_bytesToWrite);
+ QString header = "PVSMGR;" + info.fileName() + ";" + size + "\n";
+ _socket->write(header.toLocal8Bit());
+ connect(_socket, SIGNAL(readyRead()), this, SLOT(receiveAck()));
+ qDebug("[%s] Sending header...", metaObject()->className());
+}
+
+void ServerFileTransfert::receiveHeader()
+{
+ // parse header
+ QString header = QString::fromUtf8(_socket->readLine());
+ QStringList args = header.split(";");
+ QString nick = args[0];
+ QString filename = args[1];
+ _bytesToRead = args[2].toLongLong();
+ div = 1 + _bytesToRead / 1000000000; // bc. progressBar supports only int
+
+ qDebug("[%s] Received header.", metaObject()->className());
+
+ // ask user
+ QMessageBox::StandardButton result = QMessageBox::question(0,
+ tr("PVS File Transfer"),tr("User '") + nick +
+ tr("' would like to send you a file: ") + filename +
+ " (" + formatSize(_bytesToRead) + ").",
+ QMessageBox::Ok | QMessageBox::Cancel, QMessageBox::Ok);
+
+ if (result != QMessageBox::Ok)
+ {
+ sendAck(false);
+ return;
+ }
+
+ // open file
+ QString saveAs = QFileDialog::getSaveFileName(this, tr("Open File"),
+ QDir::homePath() + QDir::separator() + filename, "");
+ if (saveAs == "")
+ {
+ sendAck(false);
+ return;
+ }
+ _file = new QFile(saveAs);
+ _file->open(QIODevice::WriteOnly);
+
+ // gui
+ filenameLabel->setText(saveAs);
+ progressBar->setValue(0);
+ progressBar->setMaximum(_bytesToRead/div);
+ labelB->setText(formatSize(_bytesToRead));
+ connect(cancelButton, SIGNAL(clicked()), this, SLOT(close()));
+
+ sendAck(true);
+ show();
+}
+
+void ServerFileTransfert::sendAck(bool b)
+{
+ disconnect(_socket, SIGNAL(readyRead()), this, SLOT(receiveHeader()));
+
+ if (b)
+ {
+ QString ack = QString("ok\n");
+ _socket->write(ack.toUtf8());
+ qDebug("[%s] Sending ack...", metaObject()->className());
+ connect(_socket, SIGNAL(readyRead()), this, SLOT(receiveFile()));
+ }
+ else
+ {
+ QString ack = QString("no\n");
+ _socket->write(ack.toUtf8());
+ qDebug("[%s] Sending nack!!!", metaObject()->className());
+ close();
+ }
+}
+
+void ServerFileTransfert::receiveAck()
+{
+ QString ack = QString::fromUtf8(_socket->readLine());
+ if (ack != "ok\n")
+ {
+ qDebug("[%s] Received nack!", metaObject()->className());
+ close();
+ return;
+ }
+ qDebug("[%s] Received ack.", metaObject()->className());
+
+ disconnect(_socket, SIGNAL(readyRead()), this, SLOT(receiveAck()));
+ connect(_socket, SIGNAL(bytesWritten(qint64)), this, SLOT(sendFile()));
+ this->show();
+ qDebug("[%s] Sending file...", metaObject()->className());
+ sendFile();
+}
+
+void ServerFileTransfert::sendFile()
+{
+ if (_bytesToWrite == 0)
+ {
+ qDebug("[%s] Transfer completed.", metaObject()->className());
+ close(); // finished
+ }
+ else
+ {
+ qint64 bytesWritten = _socket->write(_file->read(1024)); // data left
+ _bytesToWrite -= bytesWritten;
+ progressBar->setValue(progressBar->value() + bytesWritten/div);
+ labelA->setText(formatSize(progressBar->value()*div));
+ }
+}
+
+void ServerFileTransfert::receiveFile()
+{
+ qint64 bytesRead = _file->write(_socket->readAll());
+ _bytesToRead -= bytesRead;
+ progressBar->setValue(progressBar->value() + bytesRead/div);
+ labelA->setText(formatSize(progressBar->value()*div));
+}
+
+void ServerFileTransfert::close()
+{
+ if (_file && _file->isOpen())
+ {
+ _file->close();
+ qDebug("[%s] File closed.", metaObject()->className());
+ }
+
+ if (_socket && _socket->isOpen())
+ {
+ disconnect(_socket, SIGNAL(readyRead()), this, SLOT(receiveAck()));
+ disconnect(_socket, SIGNAL(bytesWritten(qint64)), this, SLOT(sendFile()));
+ disconnect(_socket, SIGNAL(disconnected()), this, SLOT(close()));
+ disconnect(_socket, SIGNAL(connected()), this, SLOT(sendHeader()));
+ disconnect(_socket, SIGNAL(error(QAbstractSocket::SocketError)),
+ this, SLOT(error(QAbstractSocket::SocketError)));
+ _socket->disconnectFromHost();
+ qDebug("[%s] Connection closed.", metaObject()->className());
+ }
+
+ disconnect(cancelButton, SIGNAL(clicked()), this, SLOT(close()));
+
+ if (_bytesToWrite == 0)
+ {
+ accept();
+ QMessageBox::information(0, tr("PVS - File Transfer"),
+ tr("File Transfer complete."));
+ }
+ else
+ {
+ reject();
+ QMessageBox::warning(0, tr("PVS - File Transfer"),
+ tr("File Transfer canceled!"));
+ }
+}
+
+void ServerFileTransfert::error(QAbstractSocket::SocketError error)
+{
+ qDebug("[%s] Socket error: %i", metaObject()->className(), error);
+ close();
+}
+
+QString ServerFileTransfert::formatSize(qint64 size)
+{
+ if (size >= 1000000000) // GB
+ return QString("%1GB").arg((qreal)size / 1000000000, 0, 'f',1);
+ else if (size >= 1000000) // MB
+ return QString("%1MB").arg((qreal)size / 1000000, 0, 'f',1);
+ else if (size >= 1000) // KB
+ return QString("%1KB").arg((qreal)size / 1000, 0, 'f',1);
+ else // B
+ return QString("%1B").arg((qreal)size, 0, 'f',1);
+}