able to send file
This commit is contained in:
@@ -6,6 +6,7 @@
|
||||
#include <QStandardPaths>
|
||||
#include <QUrl>
|
||||
#include <QDebug>
|
||||
#include <QMimeDatabase>
|
||||
|
||||
AppController::AppController(QObject* parent)
|
||||
: QObject(parent)
|
||||
@@ -14,6 +15,7 @@ AppController::AppController(QObject* parent)
|
||||
, m_discovery(new LocalSend::DiscoveryManager(this))
|
||||
, m_server(new LocalSend::HttpServer(this))
|
||||
, m_sessions(new LocalSend::SessionManager(this))
|
||||
, m_httpClient(new LocalSend::HttpClient(this))
|
||||
{
|
||||
}
|
||||
|
||||
@@ -54,6 +56,17 @@ void AppController::initialize()
|
||||
connect(m_sessions, &LocalSend::SessionManager::receiveSessionCompleted,
|
||||
this, &AppController::onReceiveCompleted);
|
||||
|
||||
connect(m_httpClient, &LocalSend::HttpClient::prepareUploadResponse,
|
||||
this, &AppController::onPrepareUploadResponse);
|
||||
connect(m_httpClient, &LocalSend::HttpClient::prepareUploadError,
|
||||
this, &AppController::onPrepareUploadError);
|
||||
connect(m_httpClient, &LocalSend::HttpClient::uploadProgress,
|
||||
this, &AppController::onUploadProgress);
|
||||
connect(m_httpClient, &LocalSend::HttpClient::uploadCompleted,
|
||||
this, &AppController::onUploadCompleted);
|
||||
connect(m_httpClient, &LocalSend::HttpClient::uploadError,
|
||||
this, &AppController::onUploadError);
|
||||
|
||||
startDiscovery();
|
||||
}
|
||||
|
||||
@@ -345,3 +358,227 @@ void AppController::onReceiveCompleted(const QString& sessionId)
|
||||
{
|
||||
emit receiveCompleted(sessionId);
|
||||
}
|
||||
|
||||
bool AppController::sending() const
|
||||
{
|
||||
return !m_currentSendSessionId.isEmpty();
|
||||
}
|
||||
|
||||
double AppController::sendProgress() const
|
||||
{
|
||||
return m_sendProgress;
|
||||
}
|
||||
|
||||
void AppController::sendFiles(const QString& deviceFingerprint, const QStringList& filePaths)
|
||||
{
|
||||
if (!m_devices.contains(deviceFingerprint)) {
|
||||
emit sendError(QStringLiteral("Device not found"));
|
||||
return;
|
||||
}
|
||||
|
||||
if (filePaths.isEmpty()) {
|
||||
emit sendError(QStringLiteral("No files selected"));
|
||||
return;
|
||||
}
|
||||
|
||||
if (sending()) {
|
||||
emit sendError(QStringLiteral("Already sending files"));
|
||||
return;
|
||||
}
|
||||
|
||||
m_currentSendDeviceFingerprint = deviceFingerprint;
|
||||
m_pendingFiles = filePaths;
|
||||
m_currentFileIndex = 0;
|
||||
m_sendProgress = 0.0;
|
||||
emit sendingChanged();
|
||||
emit sendProgressChanged();
|
||||
|
||||
qDebug() << "[AppController] sendFiles: device=" << deviceFingerprint
|
||||
<< "files=" << filePaths.size();
|
||||
|
||||
LocalSend::Device target = m_devices[deviceFingerprint];
|
||||
|
||||
QMap<QString, LocalSend::FileDto> files;
|
||||
QMimeDatabase mimeDb;
|
||||
|
||||
for (int i = 0; i < filePaths.size(); ++i) {
|
||||
QString filePath = filePaths[i];
|
||||
QFileInfo info(filePath);
|
||||
|
||||
if (!info.exists()) {
|
||||
emit sendError(QStringLiteral("File not found: ") + filePath);
|
||||
m_currentSendSessionId.clear();
|
||||
emit sendingChanged();
|
||||
return;
|
||||
}
|
||||
|
||||
LocalSend::FileDto fileDto;
|
||||
fileDto.id = QString::number(i);
|
||||
fileDto.fileName = info.fileName();
|
||||
fileDto.size = info.size();
|
||||
fileDto.fileType = mimeDb.mimeTypeForFile(filePath).name();
|
||||
files.insert(fileDto.id, fileDto);
|
||||
}
|
||||
|
||||
m_currentSendSessionId = m_sessions->createSendSession(target, files,
|
||||
[filePaths]() {
|
||||
QMap<QString, QString> paths;
|
||||
for (int i = 0; i < filePaths.size(); ++i) {
|
||||
paths.insert(QString::number(i), filePaths[i]);
|
||||
}
|
||||
return paths;
|
||||
}()
|
||||
);
|
||||
|
||||
LocalSend::PrepareUploadRequestDto request;
|
||||
request.info = buildRegisterDto();
|
||||
request.files = files;
|
||||
|
||||
qDebug() << "[AppController] Sending prepare-upload request to" << target.ip;
|
||||
m_httpClient->prepareUpload(target, request);
|
||||
}
|
||||
|
||||
void AppController::cancelSend()
|
||||
{
|
||||
if (m_currentSendSessionId.isEmpty()) {
|
||||
return;
|
||||
}
|
||||
|
||||
LocalSend::Device target = m_devices.value(m_currentSendDeviceFingerprint);
|
||||
m_httpClient->cancel(target, m_currentSendSessionId);
|
||||
|
||||
m_sessions->cancelSendSession(m_currentSendSessionId);
|
||||
m_currentSendSessionId.clear();
|
||||
m_pendingFiles.clear();
|
||||
m_sendProgress = 0.0;
|
||||
emit sendingChanged();
|
||||
emit sendProgressChanged();
|
||||
}
|
||||
|
||||
void AppController::onPrepareUploadResponse(const LocalSend::PrepareUploadResponseDto& response)
|
||||
{
|
||||
qDebug() << "[AppController] onPrepareUploadResponse: sessionId=" << response.sessionId
|
||||
<< "files=" << response.files.size();
|
||||
|
||||
LocalSend::SendSession session = m_sessions->sendSession(m_currentSendSessionId);
|
||||
if (session.sessionId.isEmpty()) {
|
||||
emit sendError(QStringLiteral("Session not found"));
|
||||
m_currentSendSessionId.clear();
|
||||
emit sendingChanged();
|
||||
return;
|
||||
}
|
||||
|
||||
if (response.files.isEmpty()) {
|
||||
emit sendError(QStringLiteral("Receiver declined the transfer"));
|
||||
m_currentSendSessionId.clear();
|
||||
emit sendingChanged();
|
||||
return;
|
||||
}
|
||||
|
||||
m_sessions->setSendSessionTokens(m_currentSendSessionId, response.sessionId, response.files);
|
||||
|
||||
m_currentSendSessionId = response.sessionId;
|
||||
m_sessions->startSendSession(m_currentSendSessionId);
|
||||
|
||||
m_currentFileIndex = 0;
|
||||
sendNextFile();
|
||||
}
|
||||
|
||||
void AppController::onPrepareUploadError(const QString& error)
|
||||
{
|
||||
qWarning() << "[AppController] onPrepareUploadError:" << error;
|
||||
emit sendError(error);
|
||||
m_currentSendSessionId.clear();
|
||||
emit sendingChanged();
|
||||
}
|
||||
|
||||
void AppController::onUploadProgress(qint64 sent, qint64 total)
|
||||
{
|
||||
if (total > 0) {
|
||||
double fileProgress = static_cast<double>(sent) / total;
|
||||
int totalFiles = m_pendingFiles.size();
|
||||
double overallProgress = (m_currentFileIndex + fileProgress) / totalFiles;
|
||||
m_sendProgress = overallProgress * 100.0;
|
||||
emit sendProgressChanged();
|
||||
}
|
||||
}
|
||||
|
||||
void AppController::onUploadCompleted()
|
||||
{
|
||||
qDebug() << "[AppController] onUploadCompleted, file index:" << m_currentFileIndex;
|
||||
|
||||
m_sessions->completeSendFile(m_currentSendSessionId, m_currentSendFileId);
|
||||
|
||||
m_currentFileIndex++;
|
||||
|
||||
if (m_currentFileIndex < m_pendingFiles.size()) {
|
||||
sendNextFile();
|
||||
} else {
|
||||
qDebug() << "[AppController] All files sent successfully";
|
||||
m_sendProgress = 100.0;
|
||||
emit sendProgressChanged();
|
||||
emit sendCompleted(m_currentSendSessionId);
|
||||
m_currentSendSessionId.clear();
|
||||
emit sendingChanged();
|
||||
}
|
||||
}
|
||||
|
||||
void AppController::onUploadError(const QString& error)
|
||||
{
|
||||
qWarning() << "[AppController] onUploadError:" << error;
|
||||
emit sendError(error);
|
||||
m_sessions->failSendFile(m_currentSendSessionId, m_currentSendFileId);
|
||||
m_currentSendSessionId.clear();
|
||||
emit sendingChanged();
|
||||
}
|
||||
|
||||
void AppController::sendNextFile()
|
||||
{
|
||||
if (m_currentFileIndex >= m_pendingFiles.size()) {
|
||||
return;
|
||||
}
|
||||
|
||||
LocalSend::SendSession session = m_sessions->sendSession(m_currentSendSessionId);
|
||||
if (session.sessionId.isEmpty()) {
|
||||
qWarning() << "[AppController] Session not found:" << m_currentSendSessionId;
|
||||
return;
|
||||
}
|
||||
|
||||
QString fileId = QString::number(m_currentFileIndex);
|
||||
if (!session.files.contains(fileId)) {
|
||||
qWarning() << "[AppController] File not found in session:" << fileId;
|
||||
return;
|
||||
}
|
||||
|
||||
m_currentSendFileId = fileId;
|
||||
QString filePath = m_pendingFiles[m_currentFileIndex];
|
||||
QString token = session.files[fileId].token;
|
||||
|
||||
LocalSend::Device target = m_devices.value(m_currentSendDeviceFingerprint);
|
||||
|
||||
qDebug() << "[AppController] Uploading file" << fileId << ":" << filePath
|
||||
<< "token:" << token << "to" << target.ip;
|
||||
|
||||
if (token.isEmpty()) {
|
||||
emit sendError(QStringLiteral("No token for file: ") + fileId);
|
||||
m_currentSendSessionId.clear();
|
||||
emit sendingChanged();
|
||||
return;
|
||||
}
|
||||
|
||||
m_httpClient->uploadFile(target, m_currentSendSessionId, fileId, token, filePath);
|
||||
}
|
||||
|
||||
LocalSend::RegisterDto AppController::buildRegisterDto() const
|
||||
{
|
||||
LocalSend::RegisterDto dto;
|
||||
dto.alias = m_settings->alias();
|
||||
dto.version = m_settings->version();
|
||||
dto.deviceModel = m_settings->deviceModel();
|
||||
dto.deviceType = m_settings->deviceType();
|
||||
dto.fingerprint = m_security->fingerprint();
|
||||
dto.port = m_settings->port();
|
||||
dto.protocol = m_settings->https() ? LocalSend::ProtocolType::Https : LocalSend::ProtocolType::Http;
|
||||
dto.download = false;
|
||||
return dto;
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user