asp.net-mvcentity-frameworkasp.net-mvc-4ivalidatableobject

Two checks IValidatableObject in one entity


Is the essence of Project, the creation of which is necessary to check whether there is already an entity with the same name. When editing needs such as checking, but keep in mind that the old and the new name of the entity can be matched. You also need to display an error message. For this I use interface IValidatableObject, but do not know how to tell the Validate method the object is currently being edited or created


Solution

  • Problem is solved using method ModelState.AddModelError (string, string) in actions Edit and Create.

    [HttpPost]
    [HandleError(View="AjaxError")]
    public ActionResult Edit(ProjectsViewData data)
    {
        if (ModelState.IsValid)
        {
            if (!ContainsProject(data.CurrentObject.Name))
            {
                db.Projects.Attach(data.CurrentObject);
                db.ObjectStateManager.ChangeObjectState(data.CurrentObject, EntityState.Modified);
                db.SaveChanges();
                return Projects(data);
            }
            else
            {
                int projectId = (from p in db.Projects
                                    where p.Name == data.CurrentObject.Name
                                    select p.ProjectID).FirstOrDefault();
                if (projectId == data.CurrentObject.ProjectID)
                {
                    db.Projects.Attach(data.CurrentObject);
                    db.ObjectStateManager.ChangeObjectState(data.CurrentObject, EntityState.Modified);
                    db.SaveChanges();
                    return Projects(data);
                }
                else
                {
                    ModelState.AddModelError("Name", Localizer.ProjectAlreadyExists);
                }
            }
        }
    
        data.ObjectToEdit = data.CurrentObject;
        return Projects(data);
    }
    
    [HttpPost]
    [HandleError(View = "AjaxError")]
    public ActionResult Create(ProjectsViewData data)
    {
        if (ModelState.IsValid)
        {
            if (!ContainsProject(data.CurrentObject.Name))
            {
                db.Projects.AddObject(data.CurrentObject);
                db.SaveChanges();
                return Projects(data);
            }
            else
            {
                ModelState.AddModelError("Name", Localizer.ProjectAlreadyExists);
            }
        }
    
        data.ObjectToAdd = data.CurrentObject;
        return Projects(data);
    }
    

    Helper method:

    private bool ContainsProject(string projectName)
    {
        if (projectName != null)
        {
            projectName = Regex.Replace(projectName.Trim(), "\\s+", " ");
            List<string> projects = new List<string>();
            var projectNames = (from p in db.Projects
                                select p.Name.Trim()).ToList();
            foreach (string p in projectNames)
            {
                projects.Add(Regex.Replace(p, "\\s+", " "));
            }
            if (projects.Contains(projectName))
            {
                return true;
            }
            else
            {
                return false;
            }
        }
        else
        {
            return false;
        }
    }