Skip to content

Commit

Permalink
Implements DownloadBlock logic DynamicsValue/fake-xrm-easy#157
Browse files Browse the repository at this point in the history
  • Loading branch information
jordimontana82 committed Aug 10, 2024
1 parent 69797a8 commit 5c6158b
Show file tree
Hide file tree
Showing 4 changed files with 145 additions and 3 deletions.
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
using System;

namespace FakeXrmEasy.Core.FileStorage.Db.Exceptions
{
/// <summary>
/// Exception raised when the BlockLength property is not valid
/// </summary>
public class InvalidBlockLengthException: Exception
{
/// <summary>
/// Default constructor
/// </summary>
public InvalidBlockLengthException() : base($"The BlockLength property must be greater than zero.")
{

}
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
using System;
using FakeXrmEasy.Core.FileStorage.Download;

namespace FakeXrmEasy.Core.FileStorage.Db.Exceptions
{
/// <summary>
/// Exception raised when an Offset property is not within the range of a given file length
/// </summary>
public class InvalidOffsetException: Exception
{
/// <summary>
/// Default constructor
/// </summary>
/// <param name="properties"></param>
/// <param name="actualLength"></param>
internal InvalidOffsetException(DownloadBlockProperties properties, long actualLength)
: base($"The Offset '{properties.Offset.ToString()}' and block lengh '{properties.BlockLength.ToString()}' property values are not within the file's size of [0..{actualLength.ToString()}]")
{

}
}
}
31 changes: 29 additions & 2 deletions src/FakeXrmEasy.Core/FileStorage/Db/InMemoryFileDb.cs
Original file line number Diff line number Diff line change
Expand Up @@ -239,9 +239,36 @@ public List<FileDownloadSession> GetAllFileDownloadSessions()
return _fileDownloadSessions.Values.ToList();
}

public byte[] DownloadFileBlock(DownloadBlockProperties uploadBlockProperties)
public byte[] DownloadFileBlock(DownloadBlockProperties downloadBlockProperties)
{
throw new NotImplementedException();
var fileDownloadSession = GetFileDownloadSession(downloadBlockProperties.FileDownloadSessionId);
if (fileDownloadSession == null)
{
throw new FileTokenContinuationNotFoundException(downloadBlockProperties.FileDownloadSessionId);
}

if (downloadBlockProperties.BlockLength <= 0)
{
throw new InvalidBlockLengthException();
}

if (downloadBlockProperties.Offset < 0)
{
throw new InvalidOffsetException(downloadBlockProperties, fileDownloadSession.File.Content.Length);
}

if (downloadBlockProperties.BlockLength + downloadBlockProperties.Offset >
fileDownloadSession.File.Content.Length)
{
throw new InvalidOffsetException(downloadBlockProperties, fileDownloadSession.File.Content.Length);
}

var data = new byte[downloadBlockProperties.BlockLength];

Array.Copy(fileDownloadSession.File.Content, downloadBlockProperties.Offset, data,
0, downloadBlockProperties.BlockLength);

return data;
}
#endregion
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,8 @@ public class InMemoryFileDbDownloaderTests
private readonly FileDownloadProperties _fileDownloadProperties;
private readonly Entity _entity;
private readonly FileAttachment _file;

private readonly DownloadBlockProperties _downloadBlockProperties;

public InMemoryFileDbDownloaderTests()
{
_db = new InMemoryDb();
Expand All @@ -43,6 +44,11 @@ public InMemoryFileDbDownloaderTests()
AttributeName = "dv_file",
Content = new byte[] { 1, 2, 3, 4 }
};

_downloadBlockProperties = new DownloadBlockProperties()
{
FileDownloadSessionId = ""
};
}

[Fact]
Expand Down Expand Up @@ -93,5 +99,74 @@ public void Should_return_file_download_session_if_properties_are_valid()
Assert.Equal(_fileDownloadProperties.Target.LogicalName, _entity.LogicalName);
Assert.Equal(_fileDownloadProperties.Target.Id, _entity.Id);
}

[Fact]
public void Should_throw_file_token_continuation_not_found_exception()
{
_downloadBlockProperties.FileDownloadSessionId = "invalid id";
Assert.Throws<FileTokenContinuationNotFoundException>(() =>
_fileDb.DownloadFileBlock(_downloadBlockProperties));
}

[Theory]
[InlineData(0)]
[InlineData(-23456)]
public void Should_throw_invalid_length_exception(long blockLength)
{
_fileDb.AddFile(_file);

_entity[_fileDownloadProperties.FileAttributeName] = _file.Id;
_db.AddEntityRecord(_entity);

var fileContinuationToken = _fileDb.InitFileDownloadSession(_fileDownloadProperties);
Assert.NotNull(fileContinuationToken);

_downloadBlockProperties.FileDownloadSessionId = fileContinuationToken;
_downloadBlockProperties.BlockLength = blockLength;
Assert.Throws<InvalidBlockLengthException>(() => _fileDb.DownloadFileBlock(_downloadBlockProperties));
}

[Theory]
[InlineData(-1, 2)]
[InlineData(0, 5)]
[InlineData(2, 25)]
[InlineData(4, 2)]
public void Should_throw_invalid_offset_exception_if_exceeds_file_length(long offset, long blockLength)
{
_fileDb.AddFile(_file);

_entity[_fileDownloadProperties.FileAttributeName] = _file.Id;
_db.AddEntityRecord(_entity);

var fileContinuationToken = _fileDb.InitFileDownloadSession(_fileDownloadProperties);
Assert.NotNull(fileContinuationToken);

_downloadBlockProperties.FileDownloadSessionId = fileContinuationToken;
_downloadBlockProperties.Offset = offset;
_downloadBlockProperties.BlockLength = blockLength;
Assert.Throws<InvalidOffsetException>(() => _fileDb.DownloadFileBlock(_downloadBlockProperties));
}

[Theory]
[InlineData(0, 4)]
[InlineData(1, 3)]
[InlineData(3, 1)]
public void Should_download_a_valid_file_block(long offset, long blockLength)
{
_fileDb.AddFile(_file);

_entity[_fileDownloadProperties.FileAttributeName] = _file.Id;
_db.AddEntityRecord(_entity);

var fileContinuationToken = _fileDb.InitFileDownloadSession(_fileDownloadProperties);
Assert.NotNull(fileContinuationToken);

_downloadBlockProperties.FileDownloadSessionId = fileContinuationToken;
_downloadBlockProperties.Offset = offset;
_downloadBlockProperties.BlockLength = blockLength;
var data = _fileDb.DownloadFileBlock(_downloadBlockProperties);

Assert.Equal(blockLength, data.Length);
}
}
}

0 comments on commit 5c6158b

Please sign in to comment.