How to change dynamically entity property's display name attribute at runtime - entity-framework

Entity property look like this:
[Display(Name = "Email")]
public string Email { get; set; }
its for English,
when user select another language this attribute will change at runtime
[Display(Name = "DisplayAnotherSomething")]
public string Email { get; set; }

Related

PostgreSQL Entity Framework Code First Migration generating new table for object type JSONB field

I am using .net core 3.1
public class Person
{
public int Id { get; set; }
[Required]
[MaxLength(50)]
public string FirstName { get; set; }
[Required]
[MaxLength(50)]
public string LastName { get; set; }
[Required]
public DateTime DateOfBirth { get; set; }
**[Column(TypeName = "jsonb")]**
public IList<Address> Addresses { get; set; }
}
public class Address
{
public string Type { get; set; }
public string Company { get; set; }
public string Number { get; set; }
public string Street { get; set; }
public string City { get; set; }
}
But, when I ran add migration command that generating new table for Addresses, that I don't want
I just want to capture address list in jsonb format but not in separate table.
I am using fluent api for configuration (just for understanding above class is decorated), do we have any property where I can specify to not generate new table for any object type property.
I tried - [NotMapped] but this ignore that specific column entirely
Thank you!

Audit changes made to an owned entity Entity Framework Core

I have two entities Employer and Address
public class Employer
{
public int Code { get; set; }
public string Initials { get; set; }
public string Description { get; set; }
public virtual Address Address { get; private set; }
}
public class Address
{
public string Email { get; private set; }
public string City { get; private set; }
public string PostalCode { get; private set; }
public string AddressLine { get; private set; }
}
I have a method to track changes on both entities for audit purposes. I would like to track the changes on the owned type but I get
"System.InvalidOperationException: 'The property 'Address' on entity type 'Employer' is being accessed using the 'Property' method, but is defined in the model as a navigation property. Use either the 'Reference' or 'Collection' method to access navigation properties.'"
Any idea on how I can fix this?

EF Navigation Properties and Saves

Suppose I have these two POCOs:
public class Album {
public int ID { get; set; }
[Required]
public string Title { get; set; }
public short Rating { get; set; }
public int ArtistID { get; set; }
[Required]
public virtual Artist Artist { get; set; }
}
public class Artist {
public int ID { get; set; }
[Required]
public string Name { get; set; }
public virtual ICollection<Album> Albums { get; set; }
}
and then I execute some code like this:
using (PickContext db=new PickContext()) {
Album pick=db.Albums.SingleOrDefault(a => a.ID==pickID);
if (pick==null) return;
pick.Rating=4;
db.SaveChanges();
I was surprised that I got a validation exception like this:
Property: "Artist", Error: "The Artist field is required."
When I changed my query to include the Artist:
Album pick=db.Albums.Include("Artist").SingleOrDefault(a => a.ID==pickID);
I no longer got the exception. If I don't tell EF to populate all properties, and they're not required, will it simply overwrite these FKs in the database? I would have thought that if I retrieve an entity and don't assign a property, the property won't be changed in the database. Is this not true?
You don't need to use the required attribute for the Artist. It simply telling to EF your navigation property is always required to be there. Since you have defined,
public int ArtistID { get; set; }
as not nullable the ArtistID will be required in the in the database level (I think that is what you expected from the required attribute here). I think you can just remove the required attribute and then this should be working as expected.

EF code first uncertainty principle - referred entities may not get loaded

With automatic database recreation, it is uncertain whether referred entities will get loaded or not.
The context is EF CTP 5 and ASP.NET MVC 2. In the global.asax a database initializer is set that forces recreation of the database every time the application starts up.
Successfully retrieving an entity from a context in a controller action may still cause null reference errors when traversing references even if the references are marked as required (not null in the database). Turning off lazy loading does not make any difference.
This behaviour cannot be reproduced reliably but was observed on two different workstations (XP, 7) using Cassini.
Below are the models. Null reference exception is thrown when trying to access the NewsProvider property of the NewsFeed object. It makes no difference taking off the virtual qualifier.
public class NewsProvider
{
public int Id { get; set; }
[Required(ErrorMessage = "Please enter a name")]
[StringLength(50, ErrorMessage = "The name is too long")]
public string Name { get; set; }
}
public class NewsFeed
{
public int Id { get; set; }
[Required(ErrorMessage = "Please enter a name")]
[StringLength(50, ErrorMessage = "The name is too long")]
public string Name { get; set; }
[Required(ErrorMessage = "Please enter a URL")]
[StringLength(300, ErrorMessage = "The URL is too long")]
public string Url { get; set; }
[Required(ErrorMessage = "Please enter a news provider")]
public virtual NewsProvider NewsProvider { get; set; }
}
This is just a guess, but complex types can NEVER be null. So if you have any reference to a complex type (ICollection) you should initialize them from the Entity constructor.
Example:
public class NewsProvider
{
public int Id { get; set; }
[Required(ErrorMessage = "Please enter a name")]
[StringLength(50, ErrorMessage = "The name is too long")]
public string Name { get; set; }
}
public class NewsFeed
{
public NewsFeed() {
//Never allow NewsProvider to be null
NewsProvider = new NewsProvider();
}
public int Id { get; set; }
[Required(ErrorMessage = "Please enter a name")]
[StringLength(50, ErrorMessage = "The name is too long")]
public string Name { get; set; }
[Required(ErrorMessage = "Please enter a URL")]
[StringLength(300, ErrorMessage = "The URL is too long")]
public string Url { get; set; }
[Required(ErrorMessage = "Please enter a news provider")]
public virtual NewsProvider NewsProvider { get; set; }
}
For more info, here is a great blog post:
http://weblogs.asp.net/manavi/archive/2010/12/11/entity-association-mapping-with-code-first-part-1-one-to-one-associations.aspx

MVC Validation in Model

I'm currently using DataAnnotations to validate my MVC 2 app. However, I've ran into a small problem.
I currently have an object of type User which has a number of properties. All of which are required.
public class User
{
[Required(ErrorMessage = "Username is required")]
public string Username { get; set; }
[Required(ErrorMessage = "Password is required")]
public string Password { get; set; }
[Required(ErrorMessage = "Email is required")]
public string Email { get; set; }
[Required(ErrorMessage = "First name is required")]
public string Firstname { get; set; }
[Required(ErrorMessage = "Last name is required")]
public string Lastname { get; set; }
}
At signup, these are all mapped using the modelbinder and everything works great. However, on the "edit my detail" page only Firstname, Lastname and Email can be updated.
Whenever the view posts back and modelbinding is applied I'm getting an alert Username/Password is a required field. Even though it is not required at this point. I've thought of two ways to get around this neither of which I feel are suitable (but may be wrong)
1: Create a custom viewmodel. This will work fine, but data annotations will need to be applied to this viewmodel meaning duplicate validation on the model and the user object.
2: Include all the fields in the renderd view and post them back. This has security risks, seems really messy and wouldn't scale well to complex viewmodels.
Can anyone recommend a best practice for this situation?
There was similar question recently:
Needing to copy properties before validation. In response I have suggested creating custom ModelBinder for usage only in this particular action, and I still believe it's a best solution.
DataType
Specify the datatype of a property
DisplayName
specify the display name for a property.
DisplayFormat
specify the display format for a property like different format for Date proerty.
Required
Specify a property as required.
ReqularExpression
validate the value of a property by specified regular expression pattern.
Range
validate the value of a property with in a specified range of values.
StringLength
specify min and max length for a string property.
MaxLength
specify max length for a string property.
Bind
specify fields to include or exclude when adding parameter or form values to model properties.
ScaffoldColumn
specify fields for hiding from editor forms.
using System.ComponentModel;
using System.ComponentModel.DataAnnotations;
using System.Web.Mvc;
namespace Employee.Models
{
[Bind(Exclude = "EmpId")]
public class Employee
{
[ScaffoldColumn(false)]
public int EmpId { get; set; }
[DisplayName("Employee Name")]
[Required(ErrorMessage = "Employee Name is required")]
[StringLength(100,MinimumLength=3)]
public String EmpName { get; set; }
[Required(ErrorMessage = "Employee Address is required")]
[StringLength(300)]
public string Address { get; set; }
[Required(ErrorMessage = "Salary is required")]
[Range(3000, 10000000,ErrorMessage = "Salary must be between 3000 and 10000000")]
public int Salary{ get; set; }
[Required(ErrorMessage = "Please enter your email address")]
[DataType(DataType.EmailAddress)]
[Display(Name = "Email address")]
[MaxLength(50)]
[RegularExpression(#"[a-z0-9._%+-]+#[a-z0-9.-]+\.[a-z]{2,4}", ErrorMessage = "Please enter correct email")]
public string Email { get; set; }
}
}