Beispiel #1
0
        public UploadedFile(FileIdentifier id, IFileInfo fileInfo, StoredMetadata metadata)
        {
            this._fileInfo = fileInfo;

            this.Metadata = metadata;
            this.Id       = id;
        }
Beispiel #2
0
        private async Task StoreAsyncCore(FileIdentifier id, MultipartReader reader, CancellationToken cancellationToken)
        {
            // We need to manually read each part of the request. The browser may do as it likes and send whichever part first,
            // which means we have to build up the metadata incrementally and can only write it later

            StoredMetadataFactory metadataFactory = new StoredMetadataFactory();
            StoredMetadata        metadata        = null;

            try {
                MultipartSection section = await reader.ReadNextSectionAsync(cancellationToken);

                while (section != null)
                {
                    await this.ProcessSectionAsync(id, section, metadataFactory, cancellationToken);

                    if (metadataFactory.IsComplete() && metadata == null)
                    {
                        metadata = metadataFactory.Build();
                    }

                    section = await reader.ReadNextSectionAsync(cancellationToken);
                }

                if (metadata == null)
                {
                    throw new InvalidOperationException("Metadata is incomplete - file is not uploaded or expiration missing");
                }

                await this.StoreMetadataAsync(id, metadata, cancellationToken);

                this._logger.LogInformation(LogEvents.NewUpload, "Completed: New upload of file {0} to id {1} [{2:s}]", metadata.OriginalFileName, id, DateTime.UtcNow);
            }
            catch (OperationCanceledException ex) {
                this._logger.LogWarning(LogEvents.UploadCancelled, ex, "Upload failed due to cancellation");

                this.TryCleanup(id);
            }
            catch (InvalidDataException ex) {
                this._logger.LogError(LogEvents.UploadFailed, ex, "Upload failed due to file size exceeding");

                this.TryCleanup(id);

                throw new UploadFailedException("File size exceeded of " + reader.BodyLengthLimit.GetValueOrDefault().Bytes().Megabytes);
            }
            catch (Exception ex) {
                this._logger.LogError(LogEvents.UploadFailed, ex, "Upload failed due to exception");

                this.TryCleanup(id);

                throw new UploadFailedException("Unable to complete upload", ex);
            }
        }
Beispiel #3
0
        private async Task <UploadedFile> GetFileInternal(FileIdentifier id)
        {
            IFileInfo metadataFile = this._fileStore.GetMetadataFile(id);

            if (!metadataFile.Exists)
            {
                return(null);
            }

            IFileInfo      dataFile = this._fileStore.GetDataFile(id);
            StoredMetadata metadata = await this._metadataReader.GetMetadataAsync(metadataFile);

            return(new UploadedFile(id, dataFile, metadata));
        }
Beispiel #4
0
        public async Task <StoredMetadata> GetMetadataAsync(IFileInfo file)
        {
            StoredMetadata metadata;

            try {
                string json;
                using (StreamReader sw = new StreamReader(file.CreateReadStream())) {
                    json = await sw.ReadToEndAsync().ConfigureAwait(false);
                }

                metadata = StoredMetadata.Deserialize(json);
            } catch (Exception ex) {
                this._logger.LogError(LogEvents.UploadCorrupted, ex, "Metadata of upload at location {0} is corrupted", file.PhysicalPath);
                return(null);
            }

            return(metadata);
        }
Beispiel #5
0
        public async Task <UploadedFile> GetFileReservation(FileIdentifier id)
        {
            IFileInfo metadataFile = this._fileStore.GetMetadataFile(id);

            if (!metadataFile.Exists)
            {
                return(null);
            }

            IFileInfo dataFile = this._fileStore.GetDataFile(id);

            if (dataFile.Exists)
            {
                this._logger.LogError(LogEvents.UploadReservationTaken, "Data of uploaded file {0} has been uploaded at {1}", id, metadataFile.PhysicalPath);
                return(null);
            }

            StoredMetadata metadata = await this._metadataReader.GetMetadataAsync(metadataFile);

            return(new UploadedFile(id, dataFile, metadata));
        }
Beispiel #6
0
        public async Task <UploadedFile> GetFile(FileIdentifier id)
        {
            IFileInfo metadataFile = this._fileStore.GetMetadataFile(id);

            if (!metadataFile.Exists)
            {
                return(null);
            }

            IFileInfo dataFile = this._fileStore.GetDataFile(id);

            if (!dataFile.Exists)
            {
                this._logger.LogError(LogEvents.UploadIncomplete, "Unable to find data of uploaded file {0}, the metadata was found at path {1}", id, metadataFile.PhysicalPath);
                return(null);
            }

            StoredMetadata metadata = await this._metadataReader.GetMetadataAsync(metadataFile);

            return(new UploadedFile(id, dataFile, metadata));
        }
Beispiel #7
0
        private async Task StoreMetadataAsync(FileIdentifier id, StoredMetadata metadata, CancellationToken cancellationToken)
        {
            IFileInfo metadataFile = this._fileStore.GetMetadataFile(id);

            if (metadata.IsReservation)
            {
                StoredMetadata originalStoredMetadata = await this._metadataReader.GetMetadataAsync(metadataFile);

                if (originalStoredMetadata == null)
                {
                    this._logger.LogWarning(LogEvents.UploadFailed, "{0}: Metadata file expected for reservation at {1}", id, metadataFile.PhysicalPath);

                    throw new UploadFailedException("Missing metadata for reserved upload");
                }

                // Sync critical metadata
                metadata.Expiration = originalStoredMetadata.Expiration;
                metadata.Sender     = originalStoredMetadata.Sender;

                // Delete metadata so it can be recreated again
                this._fileWriter.Delete(metadataFile);
            }
            else
            {
                // Correct the timestamp with the upload time
                TimeSpan diff = DateTime.UtcNow - this.GetProgressObject(id).StartTime;
                metadata.Expiration += diff;
            }

            // Write away
            using (Stream fileStream = this._fileWriter.OpenWriteStream(metadataFile)) {
                using (StreamWriter sw = new StreamWriter(fileStream, Encoding.UTF8)) {
                    await sw.WriteAsync(metadata.Serialize()).ConfigureAwait(false);

                    await fileStream.FlushAsync(cancellationToken).ConfigureAwait(false);
                }
            }
        }