Hi Guys/Girls Im super new to asp.net mvc and Im trying to convert my date to a readable format. Currently it looks like this.
/Date(1444892163827)/
My Model
public class Movie
{
internal string title;
internal DateTime releasedate;
internal string genre;
public int ID { get; set; }
[Required]
public string Title { get; set; }
public DateTime ReleaseDate { get; set; }
[Required]
public string Genre { get; set; }
}
public class MovieDBContext : DbContext
{
public DbSet<Movie> Movies { get; set; }
}
My Controller
public JsonResult getAll()
{
using (MovieDBContext dataContext = new MovieDBContext())
{
var movieList = dataContext.Movies.ToList();
return Json(movieList, JsonRequestBehavior.AllowGet);
}
}
public JsonResult getMovieByNo(string MovNo)
{
using (MovieDBContext dataContext = new MovieDBContext())
{
int no = Convert.ToInt32(MovNo);
var movieList = dataContext.Movies.Find(no);
return Json(movieList, JsonRequestBehavior.AllowGet);
}
}
Any help would really be appreciated !
You need create CustomJsonResult in MVC where you use for example JSON.Net with IsoDateTimeConverter or you should change your project MVC to WebAPI if you return only JSON.
Create class from this https://stackoverflow.com/a/9302054/4599089 (Approach 2) and then use this in controller:
public JsonResult getAll()
{
using (MovieDBContext dataContext = new MovieDBContext())
{
var movieList = dataContext.Movies.ToList();
return new CustomJsonResult(){Data = movieList};
}
}
public JsonResult getMovieByNo(string MovNo)
{
using (MovieDBContext dataContext = new MovieDBContext())
{
int no = Convert.ToInt32(MovNo);
var movieList = dataContext.Movies.Find(no);
return new CustomJsonResult(){Data = movieList};
}
}
Related
Hi i have an entity and i am gonna add two tables from database named as country and state.
There is a relation between these two tables based on CountryId.
I used the "Update Model from database ..." to add these two entity types.
I have manually written two classes for these two entity-types given as below:-
public partial class Country
{
//[Key] //[DatabaseGenerated(System.ComponentModel.DataAnnotations.Schema.DatabaseGeneratedOption.Identity)]
public int CountryID { get; set; }
public string CountryName { get; set; }
}
public partial class State
{
public int StateID { get; set; }
public string StateName { get; set; }
public int CountryID { get; set; }
}
public DbSet<Country> Countries { get; set; }
public DbSet<State> States { get; set; }
Controller to fetch coutries and states :-
public JsonResult GetCountries()
{
List<Country> allCountry = new List<Country>();
using (SunilEntities dc = new SunilEntities())
{
allCountry = dc.Countries.OrderBy(a => a.CountryName).ToList();
}
return new JsonResult { Data = allCountry, JsonRequestBehavior = JsonRequestBehavior.AllowGet };
}
public JsonResult GetStates(int countryID)
{
List<State> allState = new List<State>();
using (SunilEntities dc = new SunilEntities())
{
allState = dc.States.Where(a => a.CountryID.Equals(countryID)).OrderBy(a => a.StateName).ToList();
}
return new JsonResult { Data = allState, JsonRequestBehavior = JsonRequestBehavior.AllowGet };
}
But I am getting an error "The entity type Country is not part of the model for the current context".
What should be the exact classes to be used to use these two tables in my controller?
Is there any way I can get automated classes after entity being updated with newer tables?
Under your yourmodel.edmx file there is yourmodel.tt and it generates relevant classes, thus there is no need to write these classes. By using relevant namespace you can use them.
I got the solution change models as below:-
public partial class Country
{
public Country()
{
this.States = new HashSet<State>();
}
public int CountryID { get; set; }
public string CountryName { get; set; }
public virtual ICollection<State> States { get; set; }
}
public partial class State
{
public int StateID { get; set; }
public string StateName { get; set; }
public Nullable<int> CountryID { get; set; }
public virtual Country Country { get; set; }
public virtual State State1 { get; set; }
public virtual State State2 { get; set; }
}
and change controller as given below:-
public JsonResult GetCountries()
{
using (SunilEntities dc = new SunilEntities())
{
var ret = dc.Countries.Select(x => new { x.CountryID, x.CountryName }).ToList();
return Json(ret, JsonRequestBehavior.AllowGet);
}
}
// Fetch State by Country ID
public JsonResult GetStates(int countryID)
{
using (SunilEntities dc = new SunilEntities())
{
var ret = dc.States.Where(x => x.CountryID == countryID).Select(x => new { x.StateID, x.StateName }).ToList();
return Json(ret, JsonRequestBehavior.AllowGet);
}
}
Fetch data from database some error occur here (AdminPurpose con = i.a ) Message show Cannot implicitly converted type.Please see below for my code snippets:
public JsonResult GetInfor()
{
List<AdminPurpose> all = new List<AdminPurpose>();;
using (db_Hajj_UmrahEntities dc= new db_Hajj_UmrahEntities()) {
var datas = (from a in dc.Duas join b in dc.Purposes on a.PurposeId equals b.Id
select new {
a,
b.PurPose1
});
if(datas != null) {
foreach (var i in datas)
{
AdminPurpose con = i.a ;
con.PurPose1 = i.PurPose1;
all.Add(con);
}
}
}
return new JsonResult { Data = all, JsonRequestBehavior = JsonRequestBehavior.AllowGet };
}
}
Model class one to many relation here it's using
[MetadataType(typeof(DuaMetaData))]
public partial class AdminPurpose
{
public string PurPose1 { get; set; }
}
public class DuaMetaData
{
public string Dua_Name { get; set; }
public string Arabic_Word { get; set; }
public string Translation_English { get; set; }
public string Source { get; set; }
[Display(Name = "Purpose")]
public int PurposeId { get; set; }
}
Am using controller rendering, I created one model called Footer.cs and it has below properties.
[SitecoreType(TemplateId = "{1044CFB5-2B85-4A8D-9DCC-34764D2AF5B3}", AutoMap = true)]
public class Footer
{
public virtual Item Item { get; set; }
[SitecoreField(FieldName ="Copyright Text First",FieldType = SitecoreFieldType.SingleLineText)]
public virtual string CopyrightTextFirst { get; set; }
[SitecoreField(FieldName ="Copyright Text Last",FieldType = SitecoreFieldType.SingleLineText)]
public virtual string CopyrightTextLast { get; set; }
}
In My Controller:
public ActionResult FooterTemplate()
{
ISitecoreContext ctx = new SitecoreContext();
var model = ctx.GetCurrentItem<Footer>();
return View(model);
}
But, always getting null result, please help me any one.
You can use:
public ActionResult FooterTemplate()
{
ISitecoreContext ctx = new SitecoreContext();
var model = ctx.GetCurrentItem<Footer>(RenderingContext.Current.Rendering.DataSource);
return View(model);
}
Summary:
I want a data annotation validator to reference another property in the same class (TitleAuthorAndPublishingConfiguration).
However, DB.SaveChanges() is not being called on this class directly. Rather it is being called on the parent of this class (WebsiteConfiguration).
Therefore validationContext.ObjectType is returning WebsiteConfiguration and I am unable to refer to properties of TitleAuthorAndPublishingConfiguration within the data annotation validator.
WebsiteConfiguration.cs
public class WebsiteConfiguration
{
[Key]
[DatabaseGenerated(DatabaseGeneratedOption.Identity)]
public int ID { get; set; }
public TitleAuthorAndPublishingConfiguration TitleAuthorAndPublishing { get; set; }
public BookChaptersAndSectionsConfiguration BookChaptersAndSections { get; set; }
public SocialMediaLoginsConfiguration SocialMediaLogins { get; set; }
public TagGroupsConfiguration TagGroups { get; set; }
}
public class TitleAuthorAndPublishingConfiguration
{
public string BookTitle { get; set; }
public bool IsPublished { get; set; }
// how do I access a property of current model when calling DB.SaveChanges() on parent?
[RequiredIfOtherFieldIsEnabled("IsPublished")]
public string Publisher { get; set; }
}
// ... and other sub models...
ApplicationDbContext.cs
DbSet<WebsiteConfiguration> WebsiteConfiguration {get;set;}
Example Update Code
public void SeedWebsiteConfiguration()
{
var titleAuthorAndPublishingConfiguration = new TitleAuthorAndPublishingConfiguration()
{
// seed values
};
var bookChaptersAndSectionsConfiguration = new BookChaptersAndSectionsConfiguration()
{
// seed values
};
var socialMediaLoginConfiguration = new SocialMediaLoginsConfiguration()
{
// seed values
};
var tagGroupsConfiguration = new TagGroupsConfiguration()
{
// seed values
};
var websiteConfiguration = new WebsiteConfiguration()
{
TitleAuthorAndPublishing = titleAuthorAndPublishingConfiguration,
BookChaptersAndSections = bookChaptersAndSectionsConfiguration,
SocialMediaLogins = socialMediaLoginConfiguration,
TagGroups = tagGroupsConfiguration
};
DB.WebsiteConfiguration.Add(websiteConfiguration);
DB.SaveChanges();
}
Validator Code
public class RequiredIfOtherFieldIsEnabledAttribute : ValidationAttribute
{
private string _ifWhatIsEnabled { get; set; }
public RequiredIfOtherFieldIsEnabledAttribute(string IfWhatIsEnabled)
{
_ifWhatIsEnabled = IfWhatIsEnabled;
}
protected override ValidationResult IsValid(object currentPropertyValue, ValidationContext validationContext)
{
var isEnabledProperty = validationContext.ObjectType.GetProperty(_ifWhatIsEnabled);
if (isEnabledProperty == null)
{
return new ValidationResult(
string.Format("Unknown property: {0}", _ifWhatIsEnabled)
);
}
var isEnabledPropertyValue = (bool)isEnabledProperty.GetValue(validationContext.ObjectInstance, null);
if (isEnabledPropertyValue == true)
{
if (String.IsNullOrEmpty(currentPropertyValue.ToString()))
{
return new ValidationResult(String.Format("This field is required if {0} is enabled", isEnabledProperty));
}
}
return ValidationResult.Success;
}
}
Questions
Is there a way for me to access child model properties from validationContext?
Am I misguided in my approach? Is there a better way to store multiple models as part of a larger model in a single DB table?
I was hoping not to have multiple config tables and calls to the DB. (There are 4 child models in this example, but there may be 10+ in the next app.)
The setup above meets my needs in so many ways. But I don't want to give up the functionality of DataAnnotations on the sub models!
Bonus Question
I have come across a few posts like this one:
How can I tell the Data Annotations validator to also validate complex child properties?
But that is 4 years old, and I'm wondering if anything has changed since then.
Am I trying to do something that is basically impossible (or at least very difficult)?
Am I trying to do something that is basically impossible (or at least
very difficult)?
No, there is a very simple solution that integrates perfectly with the framework and technologies using DataAnnotations.
You can create a custom ValidationAttribute that is called by EF Validation and call Validator.TryValidateObject inside. This way, when CustomValidation.IsValid is called by EF you launch child complex object validation by hand and so on for the whole object graph. As a bonus, you can gather all errors thanks to CompositeValidationResult.
i.e.
using System;
using System.ComponentModel.DataAnnotations;
using System.Collections.Generic;
public class Program
{
public static void Main() {
var person = new Person {
Address = new Address {
City = "SmallVille",
State = "TX",
Zip = new ZipCode()
},
Name = "Kent"
};
var context = new ValidationContext(person, null, null);
var results = new List<ValidationResult>();
Validator.TryValidateObject(person, context, results, true);
PrintResults(results, 0);
Console.ReadKey();
}
private static void PrintResults(IEnumerable<ValidationResult> results, Int32 indentationLevel) {
foreach (var validationResult in results) {
Console.WriteLine(validationResult.ErrorMessage);
Console.WriteLine();
if (validationResult is CompositeValidationResult) {
PrintResults(((CompositeValidationResult)validationResult).Results, indentationLevel + 1);
}
}
}
}
public class ValidateObjectAttribute: ValidationAttribute {
protected override ValidationResult IsValid(object value, ValidationContext validationContext) {
var results = new List<ValidationResult>();
var context = new ValidationContext(value, null, null);
Validator.TryValidateObject(value, context, results, true);
if (results.Count != 0) {
var compositeResults = new CompositeValidationResult(String.Format("Validation for {0} failed!", validationContext.DisplayName));
results.ForEach(compositeResults.AddResult);
return compositeResults;
}
return ValidationResult.Success;
}
}
public class CompositeValidationResult: ValidationResult {
private readonly List<ValidationResult> _results = new List<ValidationResult>();
public IEnumerable<ValidationResult> Results {
get {
return _results;
}
}
public CompositeValidationResult(string errorMessage) : base(errorMessage) {}
public CompositeValidationResult(string errorMessage, IEnumerable<string> memberNames) : base(errorMessage, memberNames) {}
protected CompositeValidationResult(ValidationResult validationResult) : base(validationResult) {}
public void AddResult(ValidationResult validationResult) {
_results.Add(validationResult);
}
}
public class Person {
[Required]
public String Name { get; set; }
[Required, ValidateObject]
public Address Address { get; set; }
}
public class Address {
[Required]
public String Street1 { get; set; }
public String Street2 { get; set; }
[Required]
public String City { get; set; }
[Required]
public String State { get; set; }
[Required, ValidateObject]
public ZipCode Zip { get; set; }
}
public class ZipCode {
[Required]
public String PrimaryCode { get; set; }
public String SubCode { get; set; }
}
I'm using LINQ-to-SQL for CRUD functionality, and DataContractJsonSerializer to serialize the object to JSON. I am also using ASP.NET MVC's data binding to post values to an MVC action that does the inserting. The problem is that it will serialize all of the properties except the Id property. I've got the model set up as so:
[Serializable]
[DataContract(Name = "campaign")]
[Table(Name = "hl.campaigns")]
public class Campaign
{
[DataMember(Name = "id")]
[Column(Name = "id", AutoSync = AutoSync.OnInsert, IsDbGenerated = true, IsPrimaryKey = true)]
public Int32 Id { get; set; }
[DataMember(Name = "createdBy")]
[Column(Name = "created_by")]
public Int32 CreatedBy { get; set; }
[DataMember(Name = "createdOnUtc")]
[Column(Name = "created_on_utc")]
public DateTime CreatedOnUtc { get; set; }
[DataMember(Name = "name")]
[Column(Name = "name", DbType = "NVarChar(256)")]
public String Name { get; set; }
/* more properties here */
}
Here is my custom JsonDataContractActionResult:
public class JsonDataContractActionResult : ActionResult
{
public JsonDataContractActionResult(Object data)
{
this.Data = data;
}
public Object Data { get; private set; }
public override void ExecuteResult(ControllerContext context)
{
var serializer = new DataContractJsonSerializer(this.Data.GetType());
String output = String.Empty;
using (var ms = new MemoryStream())
{
serializer.WriteObject(ms, this.Data);
output = Encoding.Default.GetString(ms.ToArray());
}
context.HttpContext.Response.ContentType = "application/json";
context.HttpContext.Response.Write(output);
}
}
Here's the action (JsonContract() returns a JsonDataContractActionResult):
[AcceptVerbs(HttpVerbs.Post)]
public ActionResult Modify([Bind(Prefix = "campaign")] Campaign campaign)
{
if (campaign.Id == 0)
{
try
{
CoreDB.Campaigns.InsertOnSubmit(campaign);
CoreDB.SubmitChanges();
return JsonContract(campaign);
}
catch(Exception ex)
{
// TODO: error handling
}
}
return null; // TODO: modification
}
The only thing I can think of is that somehow data binding is preventing the Id property from being serialized because it was populated after it was deserialized from the form data. Any suggestions?
What does the regular Json() method return for this object?
According to this post... there might be an issue with the automatic backing fields in C#:
http://aaron-powell.spaces.live.com/blog/cns!91A824220E2BF369!150.entry