Value on model and table keeps turning up as null - c#

I have a table called PCRStatusLog with a column called PromoteDate. This column is fed a date where data from an excel sheet was sent from staging to the primary database. It's a new column, hasn't been used yet so for most records it is null, but we need to display the data of this column to our webapp. Most of the logic to do so already exists and the models are ADO.NET entity models generated from EF Designer From Data Base in Visual Studio.
In the table, PromoteDate is DATETIME and nullable (SQL Server) and the model for the table looks like this:
public partial class PCRStatusLog
{
// ... list of fields and properties
public Nullable<System.DateTime> PromoteDate { get; set; }
}
And was generated code, not entered manually. There's nothing special about that class, it's only a list of getters/setters that map to a table, a typical simple entity model.
Here is where it is used (I didn't write most of this code, I only added changes concerning the PromoteDate):
public List<PCRTracking> GetPCRTrackingDetails()
{
//...
List<PCRTracking> pcrDetails = (from bulk in providerMasterContext.BULK_UPLOADS
join ps in providerMasterContext.PROCESSSTATUS on bulk.ProcessStatusID equals ps.ProcessStatusID
join p in providerMasterContext.PLANs on bulk.PlanCode equals p.PlanCode
where bulk.CreateDate > compDateTime
orderby bulk.BulkUploadID descending
select new PCRTracking
{
FileID = bulk.BulkUploadID,
FileName = bulk.BulkUploadActualFileName,
PlanName = p.PlanCode,
FileStatus = string.Empty,
RecordsSubmitted = 0,
RecordsFailed = 0,
ValidationStatusReports = string.Empty,
ErrorMessage = string.Empty,
Submitter = bulk.SubmissionByID,
SubmitterName = bulk.SubmissionByName,
SubmitDate = (DateTime)bulk.SubmissionDateTime
}).ToList<PCRTracking>();
foreach (PCRTracking item in pcrDetails)
{
var promoteDateQuery = (from psl in providerMasterContext.PCRStatusLogs
where psl.BulkUploadID == item.FileID
select psl).FirstOrDefault();
item.PromoteDate = promoteDateQuery.PromoteDate;
//... rest of the code doesn't make use of PromoteDate
All of the other fields in PCRTracking object work fine, but PromoteDate keeps coming up as null, even on the one record that I manually edited to have a date.
Even here, where I examine the object returned by querying the one record I know has a date under promote date, it turns out null:
// from the Main method of a test console project
var providerMasterContext = new BulkPCRDAL().providerMasterContext;
var query =(from psl in providerMasterContext.PCRStatusLogs
where psl.BulkUploadID == 43
select psl).FirstOrDefault();
foreach(var prop in query.GetType().GetProperties())
{
Console.WriteLine(prop.GetValue(query));
}
Console.ReadLine();
It grabs all the properties on the object, and everything looks right, and matches whats in the database, except this one PromoteDate property.
Am I missing something?
Note that everything else in this model works, all other fields display data from the db, this one field is the only one that won't work.

Related

How to get record form a different table based on a value from first table with linq expression?

I am not sure on linq for thisHow to get record from other table based on a value from first table with linq expression.
public IQueryable GetAllMeeting()
{
var allMeeting = from xx in _dbContext.tbl_Meeting
select new Meeting
{
Meeting_Attendee_Id = xx.Attendees,
Meeting_Agenda = xx.Agenda,
Meeting_Date = xx.Date,
Id = xx.Id,
Meeting_Subject = xx.Subject,
CreatedById = xx.Created_By
};
var meetingCreatedBy = _dbContext.tbl_User.SingleOrDefault(x=>x.Id == allMeeting.Creaated)
return allMeeting; // not sure if same thing can be done while fatching allMeetings or need to do a separate?
}
You can use let clause See Microsoft Docs
public IQueryable GetAllMeeting()
{
var allMeeting = from xx in _dbContext.tbl_Meeting
let meetingCreatedBy = _dbContext.tbl_User.FirstOrDefault(x=>x.Id == xx.CreatedById)
select new Meeting
{
Meeting_Attendee_Id = xx.Attendees,
Meeting_Agenda = xx.Agenda,
Meeting_Date = xx.Date,
Id = xx.Id,
Meeting_Subject = xx.Subject,
CreatedById = xx.Created_By,
CreatedBy = meetingCreatedBy !=null ? meetingCreatedBy.Name : "" //Or whatever property/column you have for displaying the name
};
return allMeeting;
}
Note: If these two tables are related with each other and the relationships are properly defined i.e. Created_By of table tbl_Meeting is connected with Id of tbl_User .You can simply use the navigation property to retrieve the user who created the meeting (i.e. xx.tbl_User.Name) . I would strongly recommend reading navigation properties and relationships
You need to perform join operation (probably left join) between two entities. Also add the required property inside model objec and return the value.

How to use Linq-to-SQL without having to generate all the classes?

I have never used Linq-to-Sql before in an application but I used LinqPad to develop a query and just wanted to paste it into into my code.
It's not so simple. I guessed that I need a DataContext to handle the connection but I still get errors because the view names aren't recognised.
Do I have to use the designer and create all the View/Table- classes? Is there a more simple way?
This is the query. Don't need any updates - just this one query....
var q = from user in V020
join userapp in V010 on user.SPP_USER_ID equals userapp.SPP_USER_ID
join app in V030 on userapp.SPP_AW_ID equals app.SPP_AW_ID
join tx in V040 on app.SPP_AW_ID equals tx.SPP_AW_ID
join appber in V070 on app.SPP_AW_ID equals appber.SPP_AW_ID
join ber in V050 on appber.SPP_AW_BEREICH_ID equals ber.SPP_AW_BEREICH_ID
where app.SPP_AW_AKTIV && user.SPP_USER_ID == "userid" && tx.SPP_AW_SPR == "de" && ber.SPP_AW_SPR == "de"
orderby ber.SPP_BER_SORTNB
select new {
AppName = app.SPP_AW_KURZBEZ, Url = tx.SPP_AW_URL, Label = tx.SPP_AW_NAME, Description = tx.SPP_AW_BESCHR,
Bereich = ber.SPP_AW_BERNAME,
Owner = app.SPP_AW_VERANTW, Remote = app.SPP_AW_REMOTE
}
;
Create a dbml file, as above
Open the 'server explorer'
Connect to your database
Drag the tables you wish to use from your database connection onto the designer
Party time
In EF I have used context.Database.ExecuteSQLCommand to run a stored procedure without the need to use domain modal designer (and hence generating the tables). I am sure you can do something similar in Linq to SQL. However this will not support the linq query you have. You need to move all the logic in stored procedure.
SiteManagedRepairDetails Model properties:
public long RepairID { get; set; }
public int RepairLineID { get; set; }
DAL method:
public static int UpsertData(SiteManagedRepairDetails obj)
{
XYZ.DBContexts.VoidsDBContext context = new XYZ.DBContexts.VoidsDBContext();
var results = context.Database.ExecuteSqlCommand("p_XYZDetailsUpsert #RepairID, #RepairLineID"
, new SqlParameter("#RepairID", obj.RepairID)
, new SqlParameter("#RepairLineID", obj.RepairLineID)
);
return 0;
}

Create a query using LINQ to entities with 1:N relation

I know it's not something unusual to make such kind of queries but I think I get lost so I seek help. I have to tables with relation 1:N and to make it more clear I'll post a print screen from the management studio :
I am working on a asp.net mvc 3 project and I need to make a view where all Documents will be shown (and some filter and stuff, but I think that is irrelevant for this case). I need the data from the table Documents and only one specific record for each document from the DocumentFields table. This record is the record holding the name of the Document and it's uniqueness is DocumentID == Docmuents.Id, DocumentFields.RowNo == 1 and DocumentsFields.ColumnNo == 2. This is unique record for every Document and I need to get the FieldValue from this record which actually holds the Name of the Document.
I am not very sure how to build my query (maybe using JOIN) and I also would like to make my view strongly typed passing a model of type Documents but I'm not sure if it's possible, but I think depending on the way the query is build will determine the type of the model for the view.
I believe what you want is something like this:
var results =
from d in dbContext.Documents
join df in dbContext.DocumentFields
on new { d.Id, RowNo = 1, ColumnNo = 2 } equals
new { Id = df.DocumentId, df.RowNo, df.ColumnNo }
select new
{
Document = d,
DocumentName = df.FieldValue
};
Of course if you set up navigation properties, you can just do this:
var results =
from d in dbContext.Documents
let df = d.DocumentFields.First(x => x.RowNo == 1 && x.ColumnNo == 2)
select new
{
Document = d,
DocumentName = df.FieldValue
};

What is the correct way of using Entity Framework?

I have a DB like this that I generated from EF:
Now I'd like to add a "fielduserinput" entity so I write the following code:
public bool AddValueToField(string field, string value, string userId)
{
//adds a value to the db
var context = new DBonlyFieldsContainer();
var fieldSet = (from fields in context.fieldSet
where fields.fieldName.Equals(field)
select fields).SingleOrDefault();
var userSet = (from users in context.users
where users.id.Equals(userId)
select users).SingleOrDefault();
var inputField = new fielduserinput { userInput = value, field = fieldSet, user = userSet };
return false;
}
Obviously it's not finished but I think it conveys what I'm doing.
Is this really the right way of doing this? My goal is to add a row to fielduserinput that contains the value and references to user and field. It seems a bit tedious to do it this way. I'm imagining something like:
public bool AddValueToField(string userId, string value, string fieldId)
{
var context = new db();
var newField = { field.fieldId = idField, userInput = value, user.id = userId }
//Add and save changes
}
For older versions of EF, I think you're doing more or less what needs to be done. It's one of the many reasons I didn't feel EF was ready until recently. I'm going to lay out the scenario we have to give you another option.
We use the code first approach in EF 4 CTP. If this change is important enough, read on, wait for other answers (because Flying Speghetti Monster knows I could be wrong) and then decide if you want to upgrade. Keep in mind it's a CTP not an RC, so considerable changes could be coming. But if you're starting to write a new application, I highly recommend reading some about it before getting too far.
With the code first approach, it is possible to create models that contain properties for a reference to another model and a property for the id of the other model (User & UserId). When configured correctly setting a value for either the reference or the id will set the id correctly in the database.
Take the following class ...
public class FieldUserInput{
public int UserId {get;set;}
public int FieldId {get;set;}
public virtual User User {get;set;}
public virtual Field Field {get;set;}
}
... and configuration
public class FieldUserInputConfiguration{
public FieldUserInputConfiguration(){
MapSingleType(fli => new {
userid = fli.UserId,
fieldid = fli.FieldId
};
HasRequired(fli => fli.User).HasConstraint((fli, u)=>fli.UserId == u.Id);
HasRequired(fli => fli.Field).HasConstraint((fli, f)=>fli.FieldId == f.Id);
}
}
You can write the code...
public void CreateField(User user, int fieldId){
var context = new MyContext();
var fieldUserInput = new FieldUserInput{ User = user, FieldId = fieldId };
context.FieldUserInputs.Add(fieldUserInput);
context.SaveChanges();
}
... or vice versa with the properties and everything will work out fine in the database. Here's a great post on full configuration of EF.
Another point to remember is that this level of configuration is not necessary. Code first is possible to use without any configuration at all if you stick to the standards specified in the first set of posts referenced. It doesn't create the prettiest names in the database, but it works.
Not a great answer, but figured I'd share.

How do I extract this LinqToSql data into a POCO object?

with my Repository classes, I use LinqToSql to retrieve the data from the repository (eg. Sql Server 2008, in my example). I place the result data into a POCO object. Works great :)
Now, if my POCO object has a child property, (which is another POCO object or an IList), i'm trying to figure out a way to populate that data. I'm just not too sure how to do this.
Here's some sample code i have. Please note the last property I'm setting. It compiles, but it's not 'right'. It's not the POCO object instance .. and i'm not sure how to code that last line.
public IQueryable<GameFile> GetGameFiles(bool includeUserIdAccess)
{
return (from q in Database.Files
select new Core.GameFile
{
CheckedOn = q.CheckedOn.Value,
FileName = q.FileName,
GameFileId = q.FileId,
GameType = (Core.GameType)q.GameTypeId,
IsActive = q.IsActive,
LastFilePosition = q.LastFilePosition.Value,
UniqueName = q.UniqueName,
UpdatedOn = q.UpdatedOn.Value,
// Now any children....
// NOTE: I wish to create a POCO object
// that has an int UserId _and_ a string Name.
UserAccess = includeUserIdAccess ?
q.FileUserAccesses.Select(x => x.UserId).ToList() : null
});
}
Notes:
Database.Files => The File table.
Database.FilesUserAccess => the FilesUserAccess table .. which users have access to the GameFiles / Files table.
Update
I've now got a suggestion to extract the children results into their respective POCO classes, but this is what the Visual Studio Debugger is saying the class is :-
Why is it a System.Data.Linq.SqlClient.Implementation.ObjectMaterializer<..>
.Convert<Core.GameFile> and not a List<Core.GameFile> containing the POCO's?
Any suggestions what that is / what I've done wrong?
Update 2:
this is what i've done to extract the children data into their respective poco's..
// Now any children....
UserIdAccess = includeUserIdAccess ?
(from x in q.FileUserAccesses
select x.UserId).ToList() : null,
LogEntries = includeUserIdAccess ?
(from x in q.LogEntries
select new Core.LogEntry
{
ClientGuid = x.ClientGuid,
ClientIpAndPort = x.ClientIpAndPort,
// ... snip other properties
Violation = x.Violation
}).ToList() : null
I think that all you need to do is to put another Linq query in here:
q.FileUserAccesses.Select(x => x.UserId).ToList()
i.e. You want to select data from the FileUserAccess records - which I'm assuming are Linq to SQL classes, so to do this you can have something like:
(from fua in q.FileUserAccesses
select new PocoType
{
UserID = fua.UserID,
Name = fua.User.UserName // Not sure at this point where the name comes from
}).ToList()
That should get you pointed in the right direction at least.
What is the type of UserIdAccess? How is it not 'right'? Are you getting the 'wrong' data? if so have you checked your database directly to make sure the 'right' data is there?

Categories