This commit is contained in:
2018-09-05 17:56:03 +00:00
parent a977d0d213
commit 620a27d35c
2 changed files with 52 additions and 25 deletions

View File

@@ -40,7 +40,7 @@ namespace AyaNova.Biz
inObj.Salt = Hasher.GenerateSalt();
inObj.Password = Hasher.hash(inObj.Salt, inObj.Password);
Validate(inObj, true);
Validate(inObj, null);
if (HasErrors)
return null;
else
@@ -153,14 +153,27 @@ namespace AyaNova.Biz
//put
internal bool Put(User dbObj, User inObj)
{
//Replace the db object with the PUT object skipping the password and salt and Id fields
CopyObject.Copy(inObj, dbObj, "Id, Salt, Password");
//Is the user updating the password?
if (!string.IsNullOrWhiteSpace(inObj.Password) && dbObj.Password != inObj.Password)
{
//YES password is being updated:
inObj.Password = Hasher.hash(inObj.Salt, inObj.Password);
}
else
{
//No, use the db password value
//Should not require any code to run as it will retain it's db value
}
//Replace the db object with the PUT object
CopyObject.Copy(inObj, dbObj, "Id");
//Set "original" value of concurrency token to input token
//this will allow EF to check it out
ct.Entry(dbObj).OriginalValues["ConcurrencyToken"] = inObj.ConcurrencyToken;
Validate(dbObj, false);
Validate(dbObj, inObj);
if (HasErrors)
return false;
@@ -170,10 +183,17 @@ namespace AyaNova.Biz
//patch
internal bool Patch(User dbObj, JsonPatchDocument<User> objectPatch, uint concurrencyToken)
{
//TODO: objectPatch handle patching password
//make a snapshot of the original for validation but update the original to preserve workflow
User snapshotObj=null;
CopyObject.Copy(dbObj, snapshotObj);
//Do the patching
objectPatch.ApplyTo(dbObj);
ct.Entry(dbObj).OriginalValues["ConcurrencyToken"] = concurrencyToken;
Validate(dbObj, false);
Validate(dbObj, snapshotObj);
if (HasErrors)
return false;
@@ -212,14 +232,17 @@ namespace AyaNova.Biz
//
//Can save or update?
private void Validate(User inObj, bool isNew)
private void Validate(User proposedObj, User currentObj)
{
//run validation and biz rules
if (isNew)
bool isNew = currentObj == null;
if (isNew) //Yes, no currentObj
{
//Not sure why we would care about this particular rule or why I added it? Maybe it's from widget?
// //NEW Users must be active
// if (((bool)inObj.Active) == false)
// if (((bool)proposedObj.Active) == false)
// {
// AddError(ValidationErrorType.InvalidValue, "Active", "New User must be active");
// }
@@ -228,23 +251,23 @@ namespace AyaNova.Biz
//OwnerId required
if (!isNew)
{
if (inObj.OwnerId == 0)
if (proposedObj.OwnerId == 0)
AddError(ValidationErrorType.RequiredPropertyEmpty, "OwnerId");
}
//Name required
if (string.IsNullOrWhiteSpace(inObj.Name))
if (string.IsNullOrWhiteSpace(proposedObj.Name))
AddError(ValidationErrorType.RequiredPropertyEmpty, "Name");
//Name must be less than 255 characters
if (inObj.Name.Length > 255)
if (proposedObj.Name.Length > 255)
AddError(ValidationErrorType.LengthExceeded, "Name", "255 max");
//If name is otherwise OK, check that name is unique
if (!PropertyHasErrors("Name"))
{
//Use Any command is efficient way to check existance, it doesn't return the record, just a true or false
if (ct.User.Any(m => m.Name == inObj.Name && m.Id != inObj.Id))
if (ct.User.Any(m => m.Name == proposedObj.Name && m.Id != proposedObj.Id))
{
AddError(ValidationErrorType.NotUnique, "Name");
}
@@ -278,15 +301,15 @@ namespace AyaNova.Biz
need to check open workorders and any other critical items when de-activating a user
*/
if (!inObj.UserType.IsValid())
if (!proposedObj.UserType.IsValid())
{
AddError(ValidationErrorType.InvalidValue, "UserType");
}
//Validate client type user
if (!V7ValidationImportMode && inObj.UserType == UserType.Client)
if (!V7ValidationImportMode && proposedObj.UserType == UserType.Client)
{
if (inObj.ClientId == null || inObj.ClientId == 0)
if (proposedObj.ClientId == null || proposedObj.ClientId == 0)
{
AddError(ValidationErrorType.RequiredPropertyEmpty, "ClientId");
}
@@ -298,9 +321,9 @@ namespace AyaNova.Biz
}
//Validate headoffice type user
if (!V7ValidationImportMode && inObj.UserType == UserType.HeadOffice)
if (!V7ValidationImportMode && proposedObj.UserType == UserType.HeadOffice)
{
if (inObj.HeadOfficeId == null || inObj.HeadOfficeId == 0)
if (proposedObj.HeadOfficeId == null || proposedObj.HeadOfficeId == 0)
{
AddError(ValidationErrorType.RequiredPropertyEmpty, "HeadOfficeId");
}
@@ -312,9 +335,9 @@ namespace AyaNova.Biz
}
//Validate headoffice type user
if (!V7ValidationImportMode && inObj.UserType == UserType.Subcontractor)
if (!V7ValidationImportMode && proposedObj.UserType == UserType.Subcontractor)
{
if (inObj.SubVendorId == null || inObj.SubVendorId == 0)
if (proposedObj.SubVendorId == null || proposedObj.SubVendorId == 0)
{
AddError(ValidationErrorType.RequiredPropertyEmpty, "SubVendorId");
}
@@ -325,13 +348,13 @@ namespace AyaNova.Biz
}
}
if (!inObj.Roles.IsValid())
if (!proposedObj.Roles.IsValid())
{
AddError(ValidationErrorType.InvalidValue, "Roles");
}
//Optional employee number field must be less than 255 characters
if (!string.IsNullOrWhiteSpace(inObj.EmployeeNumber) && inObj.EmployeeNumber.Length > 255)
if (!string.IsNullOrWhiteSpace(proposedObj.EmployeeNumber) && proposedObj.EmployeeNumber.Length > 255)
AddError(ValidationErrorType.LengthExceeded, "EmployeeNumber", "255 max");

View File

@@ -31,12 +31,16 @@ namespace raven_integration
Util.ValidateDataReturnResponseOk(r1);
long d1Id = r1.ObjectResponse["result"]["id"].Value<long>();
HERE
dynamic d2 = new JObject();
d2.name = Util.Uniquify("Second Test User");
d2.dollarAmount = 2.22m;
d2.active = true;
d2.roles = 0;
d2.ownerId = 1L;
d2.active=true;
d2.login=Util.Uniquify("LOGIN");
d2.password=Util.Uniquify("PASSWORD");
d2.roles=0;//norole
d2.localeId=1;//random locale
d2.userType=3;//non scheduleable
ApiResponse r2 = await Util.PostAsync("User", await Util.GetTokenAsync("manager", "l3tm3in"), d2.ToString());
Util.ValidateDataReturnResponseOk(r2);