MVC3, EF4, and Using blocks - asp.net-mvc-3

Advocation for using blocks with Entity Framework seems to be popular, but this tutorial for MVC show the Object Context for the Entity being created once at the class level. I ran into the latter first, so I had been using it. I am now trying to switch to the using block method to see if it really is faster, but am running into this error on the view:
The ObjectContext instance has been disposed and can no longer be used for operations that require a connection.
The view is trying to access a collection that was created by this:
homeView.UserList = new SelectList((from n in db.Users where n.US_INACTIVE == 0 orderby n.US_FULL_NAME select n).AsEnumerable(), "US_USER_ID", "US_FULL_NAME");
I don't understand why it is still trying to access the object context from the view (when it uses that SelectList) when it should have been populated in the controlled. Even more confusing, is this same problem does not occur for other database-populated data, which appears to make it into the view just fine.
That aside though, what do I need to do to get data from a using block into the view properly? Or, is a using block the wrong way to go for MVC, and should I just keep using once object context for the class?

You probably didn't call .ToList at the end of your expression so you are not eagerly executing any query but only building query expressions. It is only once the view is executed that the query is implicitly executed, but that happens long after your controller life has ended as well as any data contexts.
This being said I consider passing domain models to views as a bad practice. You should be using view models which are classes specifically designed to the requirements of a given view.
Ayende Rahien has a series of blog posts about the issues of view models. The view model that you pass to the view from the controller must contain all the necessary properties eagerly initialized and loaded with data and this independently of the data access technology you are using. And by the way it's not the controller's responsibility to manage your EF data contexts lifetime. That's should be specific to your data access layer (the repository).

Are you using another table in your view that is related to Users? In your current query only the Users table will be populated and accessing data in any related table will throw that error.
homeView.UserList = new SelectList((from n in db.Users.Include("Other Table") where n.US_INACTIVE == 0 orderby n.US_FULL_NAME select n).AsEnumerable(), "US_USER_ID", "US_FULL_NAME");

Related

Entity Framework returns different result with AsNoTracking

I use Entity Framework in combination with an Oracle database. If I create a query like
myLinqStatement.ToListAsync()
I get wrong data returned as a result. If I change the statement to
myLinqStatement.AsNoTracking.ToListAsync()
I get the correct data.
I also checked the native SQL query, which is generated by myLinqStatement.ToListAsync(). The generated SQL query is correct, because I get the correct data.
So is there a problem in the mapping? And why is it working with AsNoTracking?
Thanks!
What AsNoTracking does is to retrieve the data without attaching it to the context, hence any changes you apply over the data do not take effect unless you attach it again so that EF knows it should track its changes.
The code snippets you've provided do not show the whole picture, from the moment a context is created, but is it possible that other parts of your code mutate data before you call myLinqStatement.ToListAsync()?
As you mention that myLinqStatement.AsNoTracking.ToListAsync() returns expected data, makes me assume that there are some side effects in your code that AsNoTracking simply is not aware so just returns whatever it finds in your db
I came across this question because I had a similar issue with Entity Framework Core querying a DB view, the issue was cause because view didn't have a key defined, after defining a key for the entity that map to that DB view, the query returned the same result in both cases (using AsNoTracking or without using it).
In T-SQL a key for a DB view can be defined this way:
CREATE UNIQUE CLUSTERED INDEX UQ_MyDBViewName_ColumnKey
ON dbo.MyDBViewName (ColumnKey);
And in code, you can map the key using the [Key] attribute in the corresponding property of the entity or using the EF fluent API. It will depend of what the project is using.
Either way, using AsNoTracking on a query that goes directly to a DB view makes a lot of sense. Also, if for some reason the query of the view does not allow us to define a key for that view, then the option is to use AsNoTracking.
Hope it helps anyone else having the same issue.

Performance benefit? Passing Class instances or just IDs. (ASP.net MVC3)

The small web application I am working on is becoming bigger and bigger. I've noticed that when posting forms or just calling other functions I've passed parameters that consist of IDs or a whole instance of a Model class.
In a performance stand point, is it better for me to pass the whole Model object (filled with values) or should I pass the ID, then retrieve from the database?
Thanks!
For Performance benefits, you can do lot of things, common things are
1) Fetch as many as records which are needed, e.g. customized paging, in LINQ use (skip and take methods)
2) Use Data caching in controllers and Cache dependencies for Lists which are bound with View
3) Use Compiled query to fetch records. (see here)
Apply all these and see the mark-able page load speed.
EDIt: For IDs recommendations, In this question, Both will be same performance impact if you pass only ID and fetch rest of the model from database OR pass filled model.
Do not solve problems which do not exist yet. Use a tool to measure the performance problem and then try to solve.
It is always best to consider these from the use case.
For example, if I want to get an item by ID, then I pass the ID, not the whole object with the ID filled out.
I use WCF services to host my BLL and interface to my DAL, so passing data around is a costly exercise, so I do it sparingly.
If I need to update an object, I pass the object, if I just want to perform an action on an object, such as delete or get, I use the ID.
Si

"Injecting" a WHERE clause dynamically w/ PetaPoco

I'm building a multi-tenant app with a shared database using .NET MVC 3 and PetaPoco.
The tenant id (along with other info) is saved in a FormsAuth cookie on login and is available to all controllers via a BaseController property. Most tables, (i.e. apart from apart the main 'Tenants' table) include a TenantId column.
Instead of manually adding a 'WHERE TenantId = X' to all CRUD on the feature tables, is there a way I can dynamically add this to the query just before its executed? In other words, maybe maintain a list of tables, and if the query is for one of those tables, then dynamically add in the TenantId filter?
The benefit of course is that it removes the need to add in the filter manually thus reducing the chances its left out. I did find an example using NHibernate, which I doubt can be repurposed. I am using Ninject in case that makes a difference.
There is an OnCommandExecuting method on the Database class which you can override in your own sub class, and modify the sql as you wish just before it gets executed. We use this feature for converting isnull/nvl between Sql Server and Oracle.
You could just leave a marker in your sql and replace it here.

MVC3 (Models) ...what is the right way to display complex data on the view?

I’m having a philosophical problem with understanding how to use Models on MVC3.
I believe the problem lies from the fact that I come from WebForms :--)
Let's say I have 10 tables on my DB and as expected when I get them into my EF4, I get those Entity classes that represent the tables (and all their FK integer values).
When I want to display data on the View, I cannot display a select * from table because those FK integers means nothing to my users …and also because some data lies on related tables.
So my understanding is that I can create a Stored Proc, create a Complex Type that represent the actual data to display, coming from separate tables via different SQL joins.
QUESTION 1:
On the view, id MVC compliant to use as #model ..that Complex Type?
or shall I always use Models that are created on the Models folder? And if so, does that mean that I have to replicate the Complex Type on a new model inside the Models folder?
Question 2:
Is this the right way …to create specific SP to collect data that will be displayed or ..is it better to use linq and lambda to be applied to the EF4 Types that come from importing the DB into the EMDX designer.
Thoughts ??
FP
The correct way is to always define view models. View models are classes which are specifically tailored to the needs of a given view and would be defined in the MVC application tier. Those classes would contain only the properties that would be needed to be displayed by the view. Then you need to map between your domain models (EF autogenerated classes?) and the view models.
So a controller action would query a repository in order to fetch a domain model, map it to a view model and pass this view model to the view. Top facilitate this mapping you could use AutoMapper. A view shouldn't be tied to a domain model and always work with a view model. This works also the other way around: a controller action receives a view model from the view as action argument, maps it to a domain model and passes this domain model to the repository in order to perform some action with it (CRUD).
So a view model could be a class that is mapped from multiple domain models or multiple view models could be mapped to a single domain model. It all depends on how your domain looks like and how do you want to represent the information to the user.
As far as validation is concerned, I distinguish two types: UI validation and business validation. As an example of UI validation is: a field is required, or a field must be entered in a given format. A business validation is : the username is already taken or insufficient funds to perform wire transfer. UI validation should be done on the view models and business validation on the domain models.
I'm not sure why you need to use a stored proc, LINQ to Entities is able to generate complex types without needing to create stored procs (in most cases). You select subsets of data, just like you would with regular SQL.
As Darin says, the use of a View Model is appropriate for situations where you have a lot of complex data that isn't represented by a single entity. This View Model would contain multiple entities, or even multiple collections of entities. It all depends on how your data needs to be consumed.

In a MVC web application, who is responsible for filtering large collections of objects, view or model?

I have a web application built on an MVC design.
I have a database which contains a large number of objects (forum threads) which I can't load into memory at once. I now want to display (part of) this collection with different filters in effect (kinda like what stackoverflow does with questions sorted by date, votes, tags etc).
Where do I implement the filtering logic? It seems to me that this must go into the model part of the application, as only models interact with the database (in my implementation). If I make the filtering a part of the view, then the view must access the database directly to get the list of filtered objects, right? I'd like to avoid this, because it exposes the database layout to the view. But at the same time, displaying different views of the same data should be implemented in the view part of the application, as they are just that -- different views of the same data.
So how do I resolve this? Do I create an additional model, say, FilteredThreadsList, and have it remember the filter to use, and then use a FilteredView to display the list of threads that FilteredThreadsList spits out?
Or do I have to build a ThreadQueryier that allows views to query the database for certain thread objects, so I can have the filtering logic in a view without exposing the database backend?
You should never query data from the view. I don't know what framework you are using in particular but as for Ruby on Rails (should be the same for other frameworks) we always pull the necessary data from the controller and store all that information into a variable. The variable will be accessed by the view which can help you avoid querying your database directly from the view.If the code to query the database gets too lengthy in the controller, insert that code into the model instead so it's more maintainable for your project in the future. Additionally, you can call this model method from multiple places in your application if needed. Good luck!
From an architectural point of view, the model should be having the code for filtering. This is so, because in many applications the code for filtering is not trivial and has a good amount of domain logic in it. (Think of filtering top gainers from a list of stocks). From your example as well, it looks the same since you might want to filter by vote or by date or by tags and then by answered or unanswered etc.
In some very simple applications that deal with search/list of entities and allows Create/Read/Update/Delete of an entity, the pagination, sorting and filtering logic is usually very generic and can be implemented in a controller base class that is inherited by all entity-specific controller classes.
The bottom line is this: if your filtering logic is generic put it in the controller else put it in the model.
Model, that's only bunch of entities.
View provides a visual representation of the data from model - use as much of views as you want. If your application is web based, you can fetch data into browser just once (AJAX) using and re-use them for different UI components rendered in the browser.
As for what entities and what view to use for their representation, I think it's work of Controller. If you need some support for it on "model layer", add it but avoid tight coupling.

Resources