Skip to content
This repository was archived by the owner on May 14, 2024. It is now read-only.
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 2 additions & 2 deletions FileReceiver.sln
Original file line number Diff line number Diff line change
Expand Up @@ -24,13 +24,13 @@ Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "FileReceiver.Tests.Bl", "te
EndProject
Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "tests", "tests", "{165C050E-2183-4DB4-A63D-B362532F77F4}"
EndProject
Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "Integrations", "Integrations", "{C02CCF88-D61D-41B1-9E65-4DBC4580462D}"
Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "integrations", "integrations", "{C02CCF88-D61D-41B1-9E65-4DBC4580462D}"
EndProject
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "FileReceiver.Integrations.Mega", "src\FileReceiver.Integrations.Mega\FileReceiver.Integrations.Mega.csproj", "{25D09645-AC3C-40E7-8729-979B0D38F57A}"
EndProject
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "FileReceiver.Tests.Fakers", "tests\FileReceiver.Tests.Fakers\FileReceiver.Tests.Fakers.csproj", "{E421D5E4-8760-4936-BFB3-3E313EB223D1}"
EndProject
Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "Infrastructure", "Infrastructure", "{FBC36705-5D1A-4AB5-BAA2-B50CDE8C1124}"
Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "infrastructure", "infrastructure", "{FBC36705-5D1A-4AB5-BAA2-B50CDE8C1124}"
EndProject
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "FileReceiver.Infrastructure.Configuration", "src\FileReceiver.Infrastructure.Configuration\FileReceiver.Infrastructure.Configuration.csproj", "{27DC8C49-6776-4B50-AF30-AC1D87AEE754}"
EndProject
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,6 @@ public interface IFileReceivingService
Task FinishReceivingTransaction(long userId);
Task<bool> SaveDocument(long userId, Guid sessionId, Document document);
Task<FileReceivingState> GetFileReceivingStateForUser(long userId);
Task<bool> CheckIfSessionExists(Guid token);
Task<bool> CheckIfSessionExists(Guid sessionId);
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -2,12 +2,14 @@
using System.Threading.Tasks;

using FileReceiver.Common.Enums;
using FileReceiver.Common.Models;

namespace FileReceiver.Bl.Abstract.Services
{
public interface IFileReceivingSessionService
{
Task<Guid> GetId(long userId);
Task<FileReceivingSessionModel> Get(Guid sessionId);
Task CreateFileReceivingSessionAsync(long userId);
Task SetFileSizeConstraintAsync(Guid sessionId, int bytes = 1_000_000);
Task SetFileNameConstraintAsync(Guid sessionId, string regexPatterns);
Expand Down
47 changes: 40 additions & 7 deletions src/FileReceiver.Bl.Impl/Services/FileReceivingService.cs
Original file line number Diff line number Diff line change
@@ -1,11 +1,12 @@
using System;
using System.IO;
using System.Text.RegularExpressions;
using System.Threading.Tasks;

using FileReceiver.Bl.Abstract.Services;
using FileReceiver.Common.Enums;
using FileReceiver.Common.Exceptions;
using FileReceiver.Dal.Abstract.Repositories;
using FileReceiver.Common.Models;
using FileReceiver.Integrations.Mega.Abstract;

using Microsoft.Extensions.Logging;
Expand All @@ -20,7 +21,7 @@ public class FileReceivingService : IFileReceivingService
private readonly IBotMessagesService _botMessagesService;
private readonly IBotTransactionService _botTransactionService;
private readonly IBotTransactionService _transactionService;
private readonly IFileReceivingSessionRepository _fileReceivingSessionRepository;
private readonly IFileReceivingSessionService _fileReceivingSessionService;
private readonly IMegaApiClient _megaClient;
private readonly ITelegramBotClient _botClient;
private readonly ILogger<FileReceivingService> _logger;
Expand All @@ -29,15 +30,15 @@ public FileReceivingService(
IBotMessagesService botMessagesService,
IBotTransactionService botTransactionService,
IBotTransactionService transactionService,
IFileReceivingSessionRepository fileReceivingSessionRepository,
IFileReceivingSessionService fileReceivingSessionService,
IMegaApiClient megaClient,
ITelegramBotClient botClient,
ILogger<FileReceivingService> logger)
{
_botMessagesService = botMessagesService;
_botTransactionService = botTransactionService;
_transactionService = transactionService;
_fileReceivingSessionRepository = fileReceivingSessionRepository;
_fileReceivingSessionService = fileReceivingSessionService;
_megaClient = megaClient;
_botClient = botClient;
_logger = logger;
Expand All @@ -59,17 +60,30 @@ public async Task FinishReceivingTransaction(long userId)

public async Task<bool> SaveDocument(long userId, Guid sessionId, Document document)
{
// TODO: Add constraints check
var transaction = await _transactionService.Get(userId, TransactionType.FileSending);

var memStream = new MemoryStream();
var fileInfo = await _botClient.GetFileAsync(document.FileId);
await _botClient.DownloadFileAsync(fileInfo.FilePath, memStream);

var session = await _fileReceivingSessionService.Get(sessionId);

if (!IsConstraintsCompleted(session, memStream)) return false;

var megaResponse = await _megaClient.UploadFile(
transaction.Id,
sessionId.ToString(),
document.FileName,
memStream);

if (!megaResponse.Successful)
{
await _botMessagesService.SendTextMessageAsync(userId,
"An error occured while sending saving a file. " +
"*Error:* " + megaResponse.FailDescription);
transaction.TransactionState = TransactionState.Failed;
}

return megaResponse.Successful;
}

Expand All @@ -92,10 +106,29 @@ public async Task<FileReceivingState> GetFileReceivingStateForUser(long userId)
}
}

public async Task<bool> CheckIfSessionExists(Guid token)
public async Task<bool> CheckIfSessionExists(Guid sessionId)
{
var session = await _fileReceivingSessionRepository.GetByIdAsync(token);
var session = await _fileReceivingSessionService.Get(sessionId);
return session is not null;
}

private bool IsConstraintsCompleted(FileReceivingSessionModel sessionModel, MemoryStream stream)
{
var filesAmountConstraint = int.Parse(
sessionModel.Constrains.GetConstraint(ConstraintType.FileSessionMaxFiles));
if (sessionModel.FilesReceived >= filesAmountConstraint) return false;

var fileNamePattern = sessionModel.Constrains.GetConstraint(ConstraintType.FileName);
if (fileNamePattern != "-1" && !Regex.IsMatch("", fileNamePattern)) return false;

var fileSizeConstraint = int.Parse(sessionModel.Constrains.GetConstraint(ConstraintType.FileSize));
if (stream.Length > fileSizeConstraint) return false;

// TODO: Add a file's extension validation.
// It's not possible to implement simply with MemoryStream.
// This operation requires to analyze stream's content

return false;
}
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -40,6 +40,12 @@ public async Task<Guid> GetId(long userId)
return await GetSessionIdAndThrowExceptionIfNotExists(userId, nameof(GetId));
}

public async Task<FileReceivingSessionModel> Get(Guid sessionId)
{
return _mapper.Map<FileReceivingSessionModel>(
await _receivingSessionRepository.GetByIdAsync(sessionId));
}

public async Task CreateFileReceivingSessionAsync(long userId)
{
var session = new FileReceivingSessionModel
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@

<ItemGroup>
<PackageReference Include="Microsoft.Extensions.Configuration.Abstractions" Version="5.0.0" />
<PackageReference Include="Microsoft.Extensions.DependencyModel" Version="5.0.0" />
<PackageReference Include="Microsoft.OpenApi" Version="1.2.3" />
<PackageReference Include="Serilog" Version="2.10.0" />
<PackageReference Include="Serilog.Settings.Configuration" Version="3.2.0" />
Expand Down
2 changes: 0 additions & 2 deletions src/FileReceiver.Integrations.Mega/Abstract/IMegaApiClient.cs
Original file line number Diff line number Diff line change
Expand Up @@ -2,8 +2,6 @@
using System.IO;
using System.Threading.Tasks;

using FileReceiver.Integrations.Mega.Models;

namespace FileReceiver.Integrations.Mega.Abstract
{
public interface IMegaApiClient
Expand Down
11 changes: 5 additions & 6 deletions src/FileReceiver.Integrations.Mega/Impl/MegaClient.cs
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,6 @@
using CG.Web.MegaApiClient;

using FileReceiver.Integrations.Mega.Configuration;
using FileReceiver.Integrations.Mega.Models;

using Microsoft.Extensions.Options;

Expand Down Expand Up @@ -50,13 +49,13 @@ public async Task<MegaActionResponse> UploadFile(Guid transactionId, string toke
var folder = (await _client.GetNodesAsync()).FirstOrDefault(x => x.Name == token);
if (folder is null)
{
return MegaActionResponse.Fail(transactionId, token, actionDetails);
return MegaActionResponse.Fail(transactionId, token, "Suitable folder wasn't found", actionDetails);
}

var file = await _client.UploadAsync(fileAsStream, fileName, folder);
if (file is null)
{
return MegaActionResponse.Fail(transactionId, token, actionDetails);
return MegaActionResponse.Fail(transactionId, token, "File wasn't uploaded", actionDetails);
}

await _client.LogoutAsync();
Expand All @@ -79,7 +78,7 @@ public async Task<MegaActionResponse> DownloadFolder(Guid transactionId, string
var folder = (await _client.GetNodesAsync()).FirstOrDefault(x => x.Id == folderNodeInfo.Id);
if (folder is null)
{
return MegaActionResponse.Fail(transactionId, token, actionDetails);
return MegaActionResponse.Fail(transactionId, token, "Suitable folder wasn't found", actionDetails);
}

actionDetails.Data = await _client.DownloadAsync(folder);
Expand Down Expand Up @@ -114,7 +113,7 @@ public async Task<MegaActionResponse> CreateFolder(Guid transactionId, string to
var folder = await _client.CreateFolderAsync(token, root);
if (folder is null)
{
return MegaActionResponse.Fail(transactionId, token, actionDetails);
return MegaActionResponse.Fail(transactionId, token, "Suitable folder wasn't found", actionDetails);
}

actionDetails.NodeLink = (await _client.GetDownloadLinkAsync(folder)).ToString();
Expand All @@ -138,7 +137,7 @@ public async Task<MegaActionResponse> DeleteFolder(Guid transactionId, string to
var folder = (await _client.GetNodesAsync()).FirstOrDefault(x => x.Id == folderNodeInfo.Id);
if (folder is null)
{
return MegaActionResponse.Fail(transactionId, token, actionDetails);
return MegaActionResponse.Fail(transactionId, token, "Suitable folder wasn't found", actionDetails);
}

await _client.DeleteAsync(folder, false);
Expand Down
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
using System;
using System.IO;

namespace FileReceiver.Integrations.Mega.Models
namespace FileReceiver.Integrations.Mega
{
public record MegaActionResponse
{
Expand All @@ -11,6 +11,7 @@ private MegaActionResponse()

public Guid TransactionId { get; private init; }
public string Token { get; init; }
public string FailDescription { get; set; }
public bool Successful { get; init; }
public ActionDetails ActionDetails { get; private init; }

Expand All @@ -25,12 +26,17 @@ public static MegaActionResponse Success(Guid transactionId, string token, Actio
};
}

public static MegaActionResponse Fail(Guid transactionId, string token, ActionDetails details = null)
public static MegaActionResponse Fail(
Guid transactionId,
string token,
string description,
ActionDetails details = null)
{
return new MegaActionResponse()
{
Successful = false,
TransactionId = transactionId,
FailDescription = description,
Token = token,
ActionDetails = details,
};
Expand Down
6 changes: 0 additions & 6 deletions src/FileReceiverBot.Api/Controllers/BotController.cs
Original file line number Diff line number Diff line change
Expand Up @@ -27,12 +27,6 @@ public BotController(IUpdateHandlerService updateHandlerService,
[Route("/update")]
public async Task<IActionResult> ProcessTelegramMessage([FromBody] Update update)
{
_logger.LogInformation("Received a request from the bot!");
_logger.LogDebug("Received a request from the bot!");
_logger.LogWarning("Received a request from the bot!");
_logger.LogError("Received a request from the bot!");
_logger.LogCritical("Received a request from the bot!");
_logger.LogTrace("Received a request from the bot!");
await _updateHandlerServiceService.HandleUpdateAsync(update);
return Ok();
}
Expand Down
1 change: 0 additions & 1 deletion src/FileReceiverBot.Api/appsettings.json
Original file line number Diff line number Diff line change
Expand Up @@ -27,7 +27,6 @@
},
"Serilog": {
"Using": [
"Serilog.Sinks.MongoDB",
"X.Serilog.Sinks.Telegram"
],
"Enrich": [
Expand Down