diff --git a/server/AyaNova/Controllers/TranslationController.cs b/server/AyaNova/Controllers/TranslationController.cs index d4a559b2..f9312eb7 100644 --- a/server/AyaNova/Controllers/TranslationController.cs +++ b/server/AyaNova/Controllers/TranslationController.cs @@ -401,18 +401,133 @@ namespace AyaNova.Api.Controllers } - // private static void DeleteTempUploadFile(ApiUploadProcessor.ApiUploadedFilesResult uploadFormData) + // /// + // /// Put (UpdateTranslationItemDisplayText) + // /// Update a single key with new display text + // /// + // /// NewText/Id/Concurrency token object. NewText is new display text, Id is TranslationItem Id, concurrency token is required + // /// + // [HttpPut("updatetranslationitemdisplaytext")] + // public async Task PutTranslationItemDisplayText([FromBody] NewTextIdConcurrencyTokenItem inObj) // { - // if (uploadFormData.UploadedFiles.Count > 0) + // if (serverState.IsClosed) + // return StatusCode(503, new ApiErrorResponse(serverState.ApiErrorCode, null, serverState.Reason)); + + // if (!ModelState.IsValid) // { - // foreach (UploadedFileInfo a in uploadFormData.UploadedFiles) + // return BadRequest(new ApiErrorResponse(ModelState)); + // } + + // var oFromDb = await ct.TranslationItem.SingleOrDefaultAsync(z => z.Id == inObj.Id); + + // if (oFromDb == null) + // { + // return NotFound(new ApiErrorResponse(ApiErrorCode.NOT_FOUND)); + // } + + // //Now fetch translation for rights and to ensure not stock + // var oDbParent = await ct.Translation.SingleOrDefaultAsync(z => z.Id == oFromDb.TranslationId); + // if (oDbParent == null) + // { + // return NotFound(new ApiErrorResponse(ApiErrorCode.NOT_FOUND)); + // } + + // if (!Authorized.HasModifyRole(HttpContext.Items, AyaType.Translation)) + // { + // return StatusCode(403, new ApiNotAuthorizedResponse()); + // } + + // //Instantiate the business object handler + // TranslationBiz biz = TranslationBiz.GetBiz(ct, HttpContext); + + // try + // { + // if (!await biz.PutTranslationItemDisplayTextAsync(oFromDb, inObj, oDbParent)) // { - // System.IO.File.Delete(a.InitialUploadedPathName); + // return BadRequest(new ApiErrorResponse(biz.Errors)); // } // } + // catch (DbUpdateConcurrencyException) + // { + // if (!await biz.TranslationItemExistsAsync(inObj.Id)) + // { + // return NotFound(new ApiErrorResponse(ApiErrorCode.NOT_FOUND)); + // } + // else + // { + // //exists but was changed by another user + // //I considered returning new and old record, but where would it end? + // //Better to let the client decide what to do than to send extra data that is not required + // return StatusCode(409, new ApiErrorResponse(ApiErrorCode.CONCURRENCY_CONFLICT)); + // } + // } + + + // return Ok(ApiOkResponse.Response(new { Concurrency = oFromDb.Concurrency })); // } + +/// + /// Put (UpdateTranslationItemDisplayText) + /// Update a list of items with new display text + /// + /// Array of NewText/Id/Concurrency token objects. NewText is new display text, Id is TranslationItem Id, concurrency token is required + /// + [HttpPut("updatetranslationitemsdisplaytext")] + public async Task PutTranslationItemsDisplayText([FromBody] List inObj) + { + if (serverState.IsClosed) + return StatusCode(503, new ApiErrorResponse(serverState.ApiErrorCode, null, serverState.Reason)); + + if (!ModelState.IsValid) + { + return BadRequest(new ApiErrorResponse(ModelState)); + } + + var oFromDb = await ct.TranslationItem.AsNoTracking().SingleOrDefaultAsync(z => z.Id == inObj[0].Id); + + if (oFromDb == null) + { + return NotFound(new ApiErrorResponse(ApiErrorCode.NOT_FOUND)); + } + + //Now fetch translation for rights and to ensure not stock + var oDbParent = await ct.Translation.SingleOrDefaultAsync(z => z.Id == oFromDb.TranslationId); + if (oDbParent == null) + { + return NotFound(new ApiErrorResponse(ApiErrorCode.NOT_FOUND)); + } + + if (!Authorized.HasModifyRole(HttpContext.Items, AyaType.Translation)) + { + return StatusCode(403, new ApiNotAuthorizedResponse()); + } + + //Instantiate the business object handler + TranslationBiz biz = TranslationBiz.GetBiz(ct, HttpContext); + + try + { + if (!await biz.PutTranslationItemsDisplayTextAsync(inObj, oDbParent)) + { + return BadRequest(new ApiErrorResponse(biz.Errors)); + } + } + catch (DbUpdateConcurrencyException) + { + + //exists but was changed by another user + //I considered returning new and old record, but where would it end? + //Better to let the client decide what to do than to send extra data that is not required + return StatusCode(409, new ApiErrorResponse(ApiErrorCode.CONCURRENCY_CONFLICT)); + } + return NoContent(); + } + + + + #if (DEBUG) public class TranslationCoverageInfo { diff --git a/server/AyaNova/biz/TranslationBiz.cs b/server/AyaNova/biz/TranslationBiz.cs index 105ece56..1b901e42 100644 --- a/server/AyaNova/biz/TranslationBiz.cs +++ b/server/AyaNova/biz/TranslationBiz.cs @@ -79,6 +79,77 @@ namespace AyaNova.Biz return dbObject; } + + + // internal async Task PutTranslationItemDisplayTextAsync(TranslationItem dbObj, NewTextIdConcurrencyTokenItem inObj, Translation dbParent) + // { + + // if (dbParent.Stock == true) + // { + // AddError(ApiErrorCode.INVALID_OPERATION, "object", "TranslationItem is from a Stock translation and cannot be modified"); + // return false; + // } + + // //Replace the db object with the PUT object + // //CopyObject.Copy(inObj, dbObj, "Id"); + // dbObj.Display = inObj.NewText; + // //Set "original" value of concurrency token to input token + // //this will allow EF to check it out + // ct.Entry(dbObj).OriginalValues["Concurrency"] = inObj.Concurrency; + + // //Only thing to validate is if it has data at all in it + // if (string.IsNullOrWhiteSpace(inObj.NewText)) + // AddError(ApiErrorCode.VALIDATION_REQUIRED, "Display (NewText)"); + + // if (HasErrors) + // return false; + // await ct.SaveChangesAsync(); + + // //Log + // await EventLogProcessor.LogEventToDatabaseAsync(new Event(UserId, dbParent.Id, AyaType.Translation, AyaEvent.Modified), ct); + + // return true; + // } + + internal async Task PutTranslationItemsDisplayTextAsync(List inObj, Translation dbParent) + { + + if (dbParent.Stock == true) + { + AddError(ApiErrorCode.INVALID_OPERATION, "object", "TranslationItem is from a Stock translation and cannot be modified"); + return false; + } + + foreach (NewTextIdConcurrencyTokenItem tit in inObj) + { + var titem = await ct.TranslationItem.SingleOrDefaultAsync(z => z.Id == tit.Id); + if (titem == null) + { + AddError(ApiErrorCode.NOT_FOUND, $"Translation item ID {tit.Id}"); + return false; + } + //Replace the db object with the PUT object + //CopyObject.Copy(inObj, dbObj, "Id"); + titem.Display = tit.NewText; + + //Set "original" value of concurrency token to input token + //this will allow EF to check it out + ct.Entry(titem).OriginalValues["Concurrency"] = tit.Concurrency; + + //Only thing to validate is if it has data at all in it + if (string.IsNullOrWhiteSpace(tit.NewText)) + AddError(ApiErrorCode.VALIDATION_REQUIRED, $"Display (NewText) for Id: {tit.Id}"); + } + if (HasErrors) + return false; + await ct.SaveChangesAsync(); + + //Log + await EventLogProcessor.LogEventToDatabaseAsync(new Event(UserId, dbParent.Id, AyaType.Translation, AyaEvent.Modified), ct); + + return true; + } + //////////////////////////////////////////////////////////////////////////////////////////////// //DUPLICATE //