public void CreateFileRecord() { UserContext _userContext = new UserContext(); CUser user = _userContext.GetByName("Dmitrii"); FileContext _fileContext = new FileContext(); byte[] hash = Encoding.ASCII.GetBytes("0eff316809032f72e0237f8bcb1b65cb"); SqlConnection myConnection = new SqlConnection(); myConnection.ConnectionString = ConnectionContext.GetConnectionString(); myConnection.Open(); SqlTransaction myTransaction = myConnection.BeginTransaction("testTransaction"); CFile cFile = new CFile(Guid.NewGuid(), "testFile", "some/weird/path", 1024, user.Guid, true, hash, DateTime.Now, 0, 0, 0); int created = _fileContext.Create(cFile, myConnection, myTransaction); Assert.AreEqual(created, 1); }
//[Authorize] public async Task <HttpResponseMessage> UploadChunkAsync() { SqlConnection myConnection = new SqlConnection(); SqlTransaction myTransaction; using (myConnection) { myConnection.ConnectionString = ConnectionContext.GetConnectionString(); myConnection.Open(); // TRANSACTION - in case of SQL error or File write to disk error - rollback will be awailable myTransaction = myConnection.BeginTransaction("UploadFileTransaction"); try { SetUserDetails(); HttpResponseMessage response; String responseMsg; // check if such hash has record in DB. CFile newFile = _fileContext.GetByHash(fileInfo.Hash, myConnection, myTransaction); // if such hash and exist in DB and user names match if (!newFile.Guid.Equals(Guid.Empty) && newFile.UserId.Equals(user.Guid)) { response = Request.CreateResponse(HttpStatusCode.BadRequest); response.ReasonPhrase = $"Another file {newFile.Name} with same hash than{fileInfo.Name} already exists on Media Server!"; return(response); } // check if such file name has record in DB. newFile = _fileContext.GetByFileName(fileInfo.Name, user.Guid, myConnection, myTransaction); // if file with such name already exists in DB if (!newFile.Guid.Equals(Guid.Empty)) { // file exits, it has hash (so it is 100% loaded), but hash is different, which means this is the other file! if (newFile.Hash != null) { response = Request.CreateResponse(HttpStatusCode.BadRequest); response.ReasonPhrase = $"Another file {newFile.Name} with same hash than{fileInfo.Name} already exists on Media Server!"; return(response); } else { // file exists, but it has no hash, so it hasn't been 100% loaded - continue loading } } // fileName not found in DB - create new file record else { // add record to DB with file info newFile = new CFile(fileInfo, user, userFolder); // create record in DB about new file Int32 added = _fileContext.Create(newFile, myConnection, myTransaction); if (added == 0) { response = Request.CreateResponse(HttpStatusCode.BadRequest, $"Cannot add file to DB!"); return(response); } // SQL generates primary field values, so get created file back with proper Guid newFile = _fileContext.GetByFileName(newFile.Name, user.Guid, myConnection, myTransaction); // add file to all playlists specified by user. Default playlist is 'ON' if no other playlists are specified. if (fileInfo.playlists.Count == 0) { CPlaylist playlist = _playlistContext.GetByName("default", user.Guid); _fileContext.AddToPlaylist(newFile.Guid, playlist.Guid, myConnection, myTransaction); } else { // add files to other playlists specified by user foreach (CPlaylistInfo playlistInfo in fileInfo.playlists) { CPlaylist playlist = new CPlaylist(playlistInfo); _fileContext.AddToPlaylist(newFile.Guid, playlist.Guid, myConnection, myTransaction); } } } // After all checks on existing files, continue loading given chunk of byte data //todo: upload directly to memory stream or to file stream? MemoryStream ms = new MemoryStream(new byte[chunkSize], true); using (ms) { await Request.Content.CopyToAsync(ms); // check if all bytes from the chunk have been loaded (no disconnect or program crash happened during load) if (ms.Length == chunkSize) { using (FileStream fs = new FileStream (newFile.Path + newFile.Name, FileMode.Append, FileAccess.Write, FileShare.None, chunkSize, useAsync: true)) { ms.WriteTo(fs); } } else { // couldn't upload file chunk - so rollback record from DB myTransaction.Rollback(); response = Request.CreateResponse(HttpStatusCode.OK, $"Chunk has not been uploaded correctly!"); return(response); } } responseMsg = $"Chunk for file:{newFile.Name} successfully uploaded!"; // calculate Hash only if file has been loaded 100% if (isLastChunk) { // calculate Hash only if file has been loaded 100% await Task.Factory.StartNew(() => HashFile(newFile)).ContinueWith(delegate { // calculate Thumbnail for video only if file has been loaded 100% CreateThumbnail(newFile); }); responseMsg = $"File successfully uploaded!"; } // update file data in DB: hash, fileSize, ... newFile.Size += chunkSize; _fileContext.Update(newFile, myConnection, myTransaction); // if all went OK, commit records to DB myTransaction.Commit(); // return response if success response = Request.CreateResponse(HttpStatusCode.OK, responseMsg); return(response); } catch (Exception e) { myTransaction.Rollback(); HttpContext.Current.Response.StatusCode = (Int32)HttpStatusCode.BadRequest; throw new FileUploadException(e.Message, e); } } }