/// <summary> /// Open an upload stream to write to. /// </summary> /// <param name="fileName">The file name</param> /// <param name="options"><see cref="UploadOptions"/></param> /// <param name="cancelToken"><see cref="CancellationToken"/></param> public async Task <UploadStream> OpenUploadStreamAsync(string fileName, UploadOptions options = null, CancellationToken cancelToken = default(CancellationToken)) { options = options ?? new UploadOptions(); return(await CreateUploadStreamAsync(fileName, options, cancelToken) .ConfigureAwait(false)); }
// PRIVATE private async Task <UploadStream> CreateUploadStreamAsync(string filename, UploadOptions options, CancellationToken cancelToken) { Ensure.IsNotNull(options, nameof(options)); var fileInfo = new FileInfo() { Id = options.ForceFileId, Status = Status.Incomplete, FileName = filename.SafePath(), StartedAtDate = DateTimeOffset.UtcNow, Metadata = options.Metadata, ChunkSizeBytes = options.ChunkSizeBytes }; var result = await fileTable.Insert(fileInfo).RunResultAsync(conn, cancelToken) .ConfigureAwait(false); result.AssertNoErrors(); result.AssertInserted(1); //Return the real ID for the FileInfo, either generated by RethinkDB //or specified by the caller. var fileInfoId = result.GeneratedKeys?[0] ?? options.ForceFileId; return(new UploadStream(this.conn, fileInfoId, fileInfo, this.fileTable, this.chunkTable, options)); }
//PUBLIC /// <summary> /// Upload a file from a byte array. /// </summary> /// <param name="filename">The file name</param> /// <param name="source">Source bytes</param> /// <param name="options"><see cref="UploadOptions"/></param> /// <param name="cancelToken"><see cref="CancellationToken"/></param> public async Task<Guid> UploadAsync(string filename, byte[] source, UploadOptions options = null, CancellationToken cancelToken = default(CancellationToken)) { using( var ms = new MemoryStream(source) ) { return await UploadAsync(filename, ms, options, cancelToken) .ConfigureAwait(false); } }
//PUBLIC /// <summary> /// Upload a file from a byte array. /// </summary> /// <param name="filename">The file name</param> /// <param name="source">Source bytes</param> /// <param name="options"><see cref="UploadOptions"/></param> /// <param name="cancelToken"><see cref="CancellationToken"/></param> public async Task <Guid> UploadAsync(string filename, byte[] source, UploadOptions options = null, CancellationToken cancelToken = default(CancellationToken)) { using (var ms = new MemoryStream(source)) { return(await UploadAsync(filename, ms, options, cancelToken) .ConfigureAwait(false)); } }
/// <summary> /// Upload a file from a stream source. /// </summary> /// <param name="filename">The file name</param> /// <param name="source">Source stream</param> /// <param name="options"><see cref="UploadOptions"/></param> /// <param name="cancelToken"><see cref="CancellationToken"/></param> public async Task <Guid> UploadAsync(string filename, Stream source, UploadOptions options = null, CancellationToken cancelToken = default(CancellationToken)) { options = options ?? new UploadOptions(); var uploadStream = await OpenUploadStreamAsync(filename, options, cancelToken).ConfigureAwait(false); using (var destination = uploadStream) { var chunkSize = options.ChunkSizeBytes; var buffer = new byte[chunkSize]; while (true) { int bytesRead = 0; Exception sourceException = null; try { bytesRead = await source.ReadAsync(buffer, 0, buffer.Length, cancelToken) .ConfigureAwait(false); } catch (Exception ex) { sourceException = ex; } if (sourceException != null) { try { await destination.AbortAsync(cancelToken) .ConfigureAwait(false); } catch { } throw sourceException; } if (bytesRead == 0) { break; } await destination.WriteAsync(buffer, 0, bytesRead, cancelToken) .ConfigureAwait(false); } await destination.CloseAsync(cancelToken) .ConfigureAwait(false); return(destination.Id); } }
/// <summary> /// Creates an UploadStream to ReGrid. /// </summary> /// <param name="conn">RethinkDB Connection or ConnectonPool.</param> /// <param name="filesInfoId">The ID of the FileInfo in the database.</param> /// <param name="fileInfo">An incomplete FileInfo that exists in the database waiting to be finalized.</param> /// <param name="fileTable">An already namespaced Table term for FileInfo.</param> /// <param name="chunkTable">An already namespaced Table term for Chunk</param> /// <param name="options">Upload options</param> internal UploadStream(IConnection conn, Guid filesInfoId, FileInfo fileInfo, Table fileTable, Table chunkTable, UploadOptions options) : base(fileInfo) { this.conn = conn; this.filesInfoId = filesInfoId; this.fileTable = fileTable; this.chunkTable = chunkTable; this.chunkInsertOpts = options.ChunkInsertOptions; this.chunkSizeBytes = options.ChunkSizeBytes; this.batchSize = options.BatchSize; this.batch = new List<byte[]>(); sha256 = new IncrementalSHA256(); }
/// <summary> /// Upload a file from a stream source. /// </summary> /// <param name="filename">The file name</param> /// <param name="source">Source stream</param> /// <param name="options"><see cref="UploadOptions"/></param> /// <param name="cancelToken"><see cref="CancellationToken"/></param> public async Task<Guid> UploadAsync(string filename, Stream source, UploadOptions options = null, CancellationToken cancelToken = default(CancellationToken)) { options = options ?? new UploadOptions(); var uploadStream = await OpenUploadStreamAsync(filename, options, cancelToken).ConfigureAwait(false); using( var destination = uploadStream ) { var chunkSize = options.ChunkSizeBytes; var buffer = new byte[chunkSize]; while( true ) { int bytesRead = 0; Exception sourceException = null; try { bytesRead = await source.ReadAsync(buffer, 0, buffer.Length, cancelToken) .ConfigureAwait(false); } catch( Exception ex ) { sourceException = ex; } if( sourceException != null ) { try { await destination.AbortAsync(cancelToken) .ConfigureAwait(false); } catch { } throw sourceException; } if( bytesRead == 0 ) { break; } await destination.WriteAsync(buffer, 0, bytesRead, cancelToken) .ConfigureAwait(false); } await destination.CloseAsync(cancelToken) .ConfigureAwait(false); return destination.Id; } }
// PRIVATE private async Task <UploadStream> CreateUploadStreamAsync(string filename, UploadOptions options, CancellationToken cancelToken) { Ensure.IsNotNull(options, nameof(options)); var fileInfo = new FileInfo() { Status = Status.Incomplete, FileName = filename.SafePath(), StartedAtDate = DateTimeOffset.UtcNow, Metadata = options.Metadata, ChunkSizeBytes = options.ChunkSizeBytes }; var result = await fileTable.Insert(fileInfo).RunResultAsync(conn, cancelToken) .ConfigureAwait(false); result.AssertInserted(1); var fileInfoId = result.GeneratedKeys[0]; return(new UploadStream(this.conn, fileInfoId, fileInfo, this.fileTable, this.chunkTable, options)); }
/// <summary> /// Upload a file from a byte[] /// </summary> /// <param name="filename">The file name</param> /// <param name="bytes">source bytes</param> /// <param name="options"><see cref="UploadOptions"/></param> public Guid Upload(string filename, byte[] bytes, UploadOptions options = null) { return UploadAsync(filename, bytes, options).WaitSync(); }
/// <summary> /// Creates an UploadStream to ReGrid. /// </summary> /// <param name="conn">RethinkDB Connection or ConnectonPool.</param> /// <param name="filesInfoId">The ID of the FileInfo in the database.</param> /// <param name="fileInfo">An incomplete FileInfo that exists in the database waiting to be finalized.</param> /// <param name="fileTable">An already namespaced Table term for FileInfo.</param> /// <param name="chunkTable">An already namespaced Table term for Chunk</param> /// <param name="options">Upload options</param> internal UploadStream(IConnection conn, Guid filesInfoId, FileInfo fileInfo, Table fileTable, Table chunkTable, UploadOptions options) : base(fileInfo) { this.conn = conn; this.filesInfoId = filesInfoId; this.fileTable = fileTable; this.chunkTable = chunkTable; this.chunkInsertOpts = options.ChunkInsertOptions; this.chunkSizeBytes = options.ChunkSizeBytes; this.batchSize = options.BatchSize; this.batch = new List <byte[]>(); sha256 = new IncrementalSHA256(); }
/// <summary> /// Open an upload stream to write to. /// </summary> /// <param name="fileName">The file name</param> /// <param name="options"><see cref="UploadOptions"/></param> /// <param name="cancelToken"><see cref="CancellationToken"/></param> public async Task<UploadStream> OpenUploadStreamAsync(string fileName, UploadOptions options = null, CancellationToken cancelToken = default(CancellationToken)) { options = options ?? new UploadOptions(); return await CreateUploadStreamAsync(fileName, options, cancelToken) .ConfigureAwait(false); }
/// <summary> /// Open an upload stream to write to. /// </summary> /// <param name="fileName">The file name</param> /// <param name="options"><see cref="UploadOptions"/></param> public UploadStream OpenUploadStream(string fileName, UploadOptions options = null) { return OpenUploadStreamAsync(fileName, options).WaitSync(); }
// PRIVATE private async Task<UploadStream> CreateUploadStreamAsync(string filename, UploadOptions options, CancellationToken cancelToken) { Ensure.IsNotNull(options, nameof(options)); var fileInfo = new FileInfo() { Status = Status.Incomplete, FileName = filename.SafePath(), StartedAtDate = DateTimeOffset.UtcNow, Metadata = options.Metadata, ChunkSizeBytes = options.ChunkSizeBytes }; var result = await fileTable.Insert(fileInfo).RunResultAsync(conn, cancelToken) .ConfigureAwait(false); result.AssertInserted(1); var fileInfoId = result.GeneratedKeys[0]; return new UploadStream(this.conn, fileInfoId, fileInfo, this.fileTable, this.chunkTable, options); }
/// <summary> /// Open an upload stream to write to. /// </summary> /// <param name="fileName">The file name</param> /// <param name="options"><see cref="UploadOptions"/></param> public UploadStream OpenUploadStream(string fileName, UploadOptions options = null) { return(OpenUploadStreamAsync(fileName, options).WaitSync()); }
/// <summary> /// Upload a file from a byte[] /// </summary> /// <param name="filename">The file name</param> /// <param name="bytes">source bytes</param> /// <param name="options"><see cref="UploadOptions"/></param> public Guid Upload(string filename, byte[] bytes, UploadOptions options = null) { return(UploadAsync(filename, bytes, options).WaitSync()); }
/// <summary> /// Upload a file from a stream /// </summary> /// <param name="filename">The file name</param> /// <param name="stream">source stream</param> /// <param name="options"><see cref="UploadOptions"/></param> public Guid Upload(string filename, Stream stream, UploadOptions options = null) { return(UploadAsync(filename, stream, options).WaitSync()); }
/// <summary> /// Upload a file from a stream /// </summary> /// <param name="filename">The file name</param> /// <param name="stream">source stream</param> /// <param name="options"><see cref="UploadOptions"/></param> public Guid Upload(string filename, Stream stream, UploadOptions options = null) { return UploadAsync(filename, stream, options).WaitSync(); }