I'm working on a project where a record needs to be inserted, using a context class. However, before the insertion, one of the properties 'DataArea' is being set to a value that it should not have.
I started debugging the code to see where exactly this value is being set, and I have altered the short written version of the getter and setter (get; set;), to this:
public DataAreaEnum _DataArea;
public DataAreaEnum DataArea
{
get
{
return _DataArea;
}
set
{
_DataArea = value;
Debugger.Break();
}
}
By doing this, I had hoped that the debugger would break when the value was being set, however this is never hit. I am stuck and do not know how to think about this. Are there any other ways this value could have been set? How can I found out where this value was being set, if the breakpoint in the setter is never hit?
The complete class code:
using Works.Common.Models;
using System.Collections.Generic;
using System.Diagnostics;
namespace Works.Models.Toolsheets
{
public partial class Toolblad : ModelBase
{
public Toolblad()
{
Bijlagen = new HashSet<Bijlage>();
//Carrousels = new HashSet<Carrousel>();
KlauwplaatSlijpers = new HashSet<KlauwplaatSlijper>();
Klauwplaten = new HashSet<Klauwplaat>();
Laadtafels = new HashSet<Laadtafel>();
Laders = new HashSet<Lader>();
MblStangenLaders = new HashSet<MblStangenLader>();
MblStangenLaderWisselpunten = new HashSet<MblStangenLaderWisselpunt>();
Shuttles = new HashSet<Shuttle>();
Spankoppen = new HashSet<Spankop>();
SpankopSlijpers = new HashSet<SpankopSlijper>();
Revolvers = new HashSet<ToolbladRevolver>();
}
public DataAreaEnum _DataArea;
public DataAreaEnum DataArea
{
get
{
return _DataArea;
}
set
{
_DataArea = value;
Debugger.Break();
}
}
public bool IsTemplate { get; set; }
#region Navigation Properties
public virtual AlgemeneInfo AlgemeneInfo { get; set; }
public int AlgemeneInfoId { get; set; }
public ICollection<Bijlage> Bijlagen { get; set; }
//public ICollection<Carrousel> Carrousels { get; set; }
public ICollection<KlauwplaatSlijper> KlauwplaatSlijpers { get; set; }
public ICollection<Klauwplaat> Klauwplaten { get; set; }
public ICollection<Laadtafel> Laadtafels { get; set; }
public ICollection<Lader> Laders { get; set; }
public MachineGroep MachineGroep { get; set; }
public int MachineGroepId { get; set; }
public ICollection<MblStangenLader> MblStangenLaders { get; set; }
public ICollection<MblStangenLaderWisselpunt> MblStangenLaderWisselpunten { get; set; }
public ICollection<ToolbladRevolver> Revolvers { get; set; }
public ICollection<Shuttle> Shuttles { get; set; }
public ICollection<Spankop> Spankoppen { get; set; }
public ICollection<SpankopSlijper> SpankopSlijpers { get; set; }
#endregion Navigation Properties
}
}
I note that Toolblad is a partial class. Is there any code elsewhere changing _DataArea? Try renaming it to something else (e.g. _dataArea) just in that code file and see if it all still compiles.
Doing that will catch any unexpected code that tries to access it.
Whether you set the value of a Enum or not, it defaults to 0 which is why you are seeing a value for it without setting one.
Related
Below C# code
ResBlock resBlock1 = new ResBlock();
resBlock1.CustomerID = "ABC";
Block block = new Block();
block.Tag = resBlock1;
resBlock1 = null;
Console.WriteLine(((ResBlock)block.Tag).CustomerID);
The output would be "ABC". Of course this is the example of what I am facing but my code is way more complicated.
What I would like to understand is if there is a way to get block.Tag = null when the referenced object (resBlock1) is set to null or destroyed in some other way (which one?).
Classes are very simple as this is just an example:
public class ResBlock: IDisposable
{
public DateTime From { get; set; }
public DateTime To { get; set; }
public string CustomerID { get; set; }
public string ItemID { get; set; }
[...]
public ResBlock() {
DaysStatus = new List<ResBlockDayStatus>();
Deleted = false;
}
public bool LogicallyDeleted { get; set; }
public void Dispose() { }
}
public class Block
{
public bool Selected { get; set; }
public object Tag { get; set; }
public DateTime From { get; set; }
public DateTime To { get; set; }
}
No. You can't "destroy" an object in that way. That's just not the way that object lifetimes work in .NET. You could potentially change the Tag property to a WeakReference. That would prevent the Tag property from keeping the object within the WeakReference alive... but you still wouldn't be able to actively request object destruction.
I have the following example schema:
public class CounterReading
{
public int CounterReadingId { get; set; }
public virtual Counter Counter { get; set; }
public DateTime Date { get; set; }
public decimal Reading { get; set; }
public CounterReading()
{
Date = DateTime.Now;
}
}
public class Counter
{
[Key, ForeignKey("Meter")]
public int CounterId { get; set; }
public virtual Meter Meter { get; set; }
public virtual ObservableCollection<CounterReading> Readings { get; set; }
[NotMapped]
public CounterReading CurrentReading
{
get
{
if(Readings.Count > 0)
{
return Readings.MaxBy(m => m.Reading);
}
return null;
}
}
}
public abstract class Meter
{
public int MeterId { get; set; }
public string EANNumber { get; set; }
public string MeterNumber { get; set; }
public virtual Premise Premise { get; set; }
}
public class WaterMeter : Meter
{
public virtual Counter Counter { get; set; }
public WaterMeter()
{
Counter = new Counter();
Counter.Readings = new ObservableCollection<CounterReading>();
}
}
And what doesn't work is that my WaterMeter does not have any CounterReadings when I load it from database. This is because I set my Counter in my constructor, to avoid NullReferencesExceptions when I create a new WaterMeter in runtime.
If I remove my WaterMeterconstructor, EF loads my readings just fine. But that means I have loads of NullReferences when using my application without reloading my data each and every time.
What's the best way to solve this?
Edit:
NRE:
Well firstly, there is a disjoint in the code you have in your question and the actual code you are executing (as per the image you added) which is why I couldn't see a problem.
However, from the image you posted it's clear that the problem is the fact that you have Readings as a private field - EF CodeFirst requires navigation properties to be marked as public virtual in order for them to be initialised.
To avoid null reference exception with collection, you should introduce local readonly collection field and initialize it empty collection.
public class Counter
{
private readonly ObservableCollection<CounterReading> readings = new ObservableCollection<CounterReading>();
public virtual ObservableCollection<CounterReading> Readings
{
get { return readings; }
set { readings = value; }
}
[Key, ForeignKey("Meter")]
public int CounterId { get; set; }
public virtual Meter Meter { get; set; }
[NotMapped]
public CounterReading CurrentReading
{
get
{
return Readings.MaxBy(m => m.Reading);
}
}
}
I've got one addition to Evgeny's answer. Instead of always creating a new instance of the collection , you can make it conditionally so it only creates a new instance when this property is actually called:
private readonly ObservableCollection<CounterReading> readings;
public virtual ObservableCollection<CounterReading> Readings
{
get
{
if(_readings == null)
{
_readings = new ObservableCollection<CounterReading>();
}
return readings;
}
set { readings = value; }
}
If you don't need to add logic to the getter and setter, why don't you consider using this:
public virtual ObservableCollection<CounterReading> Readings {get;set;}
I have read several questions and answers on this topic, it seems to be a fairly common topic, but none have so far been able to help me.
I am using Visual Studio 2013 and entity framework and trying to create a local report from an object and display it in the reportviewer.
When I run it the report headers show but no data despite the fact that my GetConstraints() method is called and runs without a problem.
The model for the data has been kept fairly simple:
public class ConstraintDataModel
{
public string name { get; set; }
public int interval { get; set; }
public string complianceEntity { get; set; }
public string inspectionEntity { get; set; }
public string nominalValue { get; set; }
public int taskID { get; set; }
public string installations { get; set; }
public int groupTask { get; set; }
public string lastInspectionDate { get; set; }
public string nextInspectionDate { get; set; }
public int missed { get; set; }
public string rating { get; set; }
}
As has the method for returning it:
public static List<ConstraintDataModel> GetConstraints()
{
List<ConstraintDataModel> constraintList = new List<ConstraintDataModel>();
List<ICMConstraint> constraints = (List<ICMConstraint>)ctx.ICMConstraints.Where(cust => cust.CustomerID.Equals(1001)).ToList();
foreach (ICMConstraint constraint in constraints)
{
ConstraintDataModel constraintsModel = new ConstraintDataModel();
constraintsModel.taskID = constraint.ConstraintID;
constraintsModel.name = constraint.Name;
constraintsModel.complianceEntity = GetEntityName(constraint.ComplianceEntityID);
constraintsModel.inspectionEntity = GetEntityName(constraint.InspectionEntityID);
constraintsModel.installations = GetInstallations(constraint.ConstraintID);
constraintsModel.interval = constraint.Interval;
constraintsModel.nextInspectionDate = constraint.NextInspectionDate.ToShortDateString();
constraintsModel.missed = constraint.MissedInspections;
constraintsModel.nominalValue = constraint.NominalValue;
constraintsModel.rating = GetConstraintRating(constraint.ConstraintID);
}
return constraintList;
}
I have followed a few tutorials and haven't deviated from them. I have also tried explicitly binding the data on Page_Load but that doesn't help.
I am not sure what other code to post so if anything else is need just say.
Don't you need to add the object to the list you are returning:
}
return constraintList;
to this:
constraintList.Add(constraintsModel);
}
return constraintList;
I'm trying to sort out this issue but as I'm learning a lot of this stuff as I go along I'd really appreciate it if someone could explain where I'm going wrong and/or some good resources where I can read up.
So, I have a model based on my Entity Framework model of my database and a viewmodel representing properties in that model. I've built a Kendo grid to display the data (defined in a js file) and the method in the contoller returns a Json result set. Trouble is, when I try to display a value in a joined db table, if there hasn't been a key value set, I get a nullreferenceexception error. Obviously I'm missing part of the puzzle here as there must be a way of coding this to stop it happening. Any help would be gratefully received!
My model is like this:
namespace TrainingKendoUI.Models
{
using System;
using System.Collections.Generic;
public partial class TRAINING_EMPLOYEE_COURSES
{
public int EMP_COURSE_ID { get; set; }
public int EMPLOYEE_ID { get; set; }
public int COURSE_ID { get; set; }
public Nullable<System.DateTime> DATE_ATTENDED { get; set; }
public Nullable<decimal> COURSE_COST { get; set; }
public string COURSE_RESITS { get; set; }
public Nullable<int> PROVIDER_ID { get; set; }
public Nullable<int> EMP_COURSE_STATUS_ID { get; set; }
public Nullable<int> VENUE_ID { get; set; }
public virtual TRAINING_COURSES TRAINING_COURSES { get; set; }
public virtual TRAINING_EMPLOYEE_COURSE_STATUS TRAINING_EMPLOYEE_COURSE_STATUS { get; set; }
public virtual TRAINING_EMPLOYEES TRAINING_EMPLOYEES { get; set; }
public virtual TRAINING_PROVIDERS TRAINING_PROVIDERS { get; set; }
public virtual TRAINING_VENUES TRAINING_VENUES { get; set; }
}
}
My controller method looks like this:
public JsonResult EmployeeCourses_Read()
{
var model = db.TRAINING_EMPLOYEE_COURSES;
var ViewModel = new List<EmployeeCoursesIntersectionViewModel>();
foreach (var employee in model)
{
ViewModel.Add(new EmployeeCoursesIntersectionViewModel(employee));
}
return Json(ViewModel, JsonRequestBehavior.AllowGet);
}
and my view model lilke this:
namespace TrainingKendoUI.ViewModels
{
public class EmployeeCoursesIntersectionViewModel
{
#region Constructors
public EmployeeCoursesIntersectionViewModel()
{
}
public EmployeeCoursesIntersectionViewModel(TRAINING_EMPLOYEE_COURSES model)
{
this.empCourseId = model.EMP_COURSE_ID;
this.employee = model.TRAINING_EMPLOYEES.FIRST_NAME;
this.course = model.TRAINING_COURSES.COURSE_NAME;
this.dateAttended = model.DATE_ATTENDED;
this.cost = model.COURSE_COST;
this.resits = model.COURSE_RESITS;
//These lines will produce a NullReference error if not set through the front end...
this.provider = model.TRAINING_PROVIDERS.PROVIDER_NAME;
this.status = model.TRAINING_EMPLOYEE_COURSE_STATUS.EMP_COURSE_STATUS;
this.venue = model.TRAINING_VENUES.VENUE_NAME;
}
#endregion
#region Properties
public int empCourseId { get; set; }
public string employee { get; set; }
public string course { get; set; }
public Nullable<System.DateTime> dateAttended { get; set; }
public Nullable<decimal> cost { get; set; }
public string resits { get; set; }
public string provider { get; set; }
public string status { get; set; }
public string venue { get; set; }
#endregion
}
}
Do a null check on the object before setting it, i.e.
this.provider = model.TRAINING_PROVIDERS == null ? ""
: model.TRAINING_PROVIDERS.PROVIDER_NAME;
and you'll have to do similar for status and venue
this.status = model.TRAINING_EMPLOYEE_COURSE_STATUS== null ? ""
model.TRAINING_EMPLOYEE_COURSE_STATUS.EMP_COURSE_STATUS;
this.venue = model.TRAINING_VENUES== null ? ""
model.TRAINING_VENUES.VENUE_NAME;
I've done the googling to no avail. This is the one sole error preventing my code from compiling and running but I can't seem to figure it out. The exact text of the error is "...Dictionary is less accessible than property FleetAirliner.InsuranceProperties"
Any ideas what could be causing this?
namespace TheAirline.Model.AirlinerModel
{
[Serializable]
public class FleetAirliner
{
public Airliner Airliner { get; set; }
public string Name { get; set; }
public Airport Homebase { get; set; }
public enum PurchasedType { Bought, Leased,BoughtDownPayment }
public DateTime PurchasedDate { get; set; }
public PurchasedType Purchased { get; set; }
public Boolean HasRoute { get { return this.Routes.Count > 0; } set { ;} }
public AirlinerStatistics Statistics { get; set; }
/*Changed for deleting routeairliner*/
public enum AirlinerStatus { Stopped, On_route, On_service, Resting, To_homebase, To_route_start }
public AirlinerStatus Status { get; set; }
public Coordinates CurrentPosition { get; set; }
public List<Route> Routes { get; private set; }
public Flight CurrentFlight { get; set; }
public DateTime GroundedToDate { get; set; }
public List<Pilot> Pilots { get; set; }
public Dictionary<string, AirlinerInsurance> InsurancePolicies { get; set; } //error occurs here
public int NumberOfPilots {get {return this.Pilots.Count;} private set {;}}
public FleetAirliner(PurchasedType purchased,DateTime purchasedDate, Airline airline,Airliner airliner,Airport homebase)
{
this.Airliner = airliner;
this.Purchased = purchased;
this.PurchasedDate = purchasedDate;
this.Airliner.Airline = airline;
this.Homebase = homebase;
this.Name = airliner.TailNumber;
this.Statistics = new AirlinerStatistics(this);
this.Status = AirlinerStatus.Stopped;
this.CurrentPosition = new Coordinates(this.Homebase.Profile.Coordinates.Latitude, this.Homebase.Profile.Coordinates.Longitude);
this.Routes = new List<Route>();
this.Pilots = new List<Pilot>();
this.InsurancePolicies = new Dictionary<string, AirlinerInsurance>();
}
It means that class "AirlinerInsurance" Is not Public.
It is a property that is public, but other classes, that are allowed to use the property, might not have access rights to the class itself (it is private / internal).
Edit
Now that you have posted the code of class "AirlinerInsurance", just add a "public" modifier to it.
You can read more about it here and here
you need
class AirlinerInsurance {
// stuff
}
to be
public class AirlinerInsurance {
//stuff
}