ASP.NET MVC - getting started with Linq and SQL procedure - asp.net

Today is my first day using ASP.NET MVC, and I'm finding it very intriguing. I only just started learning asp.net.
So basically I'm trying to call a procedure from an MSSQL database, and with it I need to send a paramater "PlaceID", which is an integer. This procedure basically just picks out a number of columns from different tables in the database. Here is the Linq to SQL code
The ultimate goal is to be able to retrieve all the information and return it as JSON with a function that will be available for a javascript.
I'm wondering what is the best way to proceed from here. I know I have to create a view, but I'm still unclear exactly on how I can call the procedure and make it store all the information. I could really use some help on this, some code examples would be excellent. I already wrote a C#.net function to convert a datatable to JSON using a stringbuilder, but I get the feeling there is a smarter way to do things.
Any help is very appreciated.

Might I suggest going through the NerdDinner.com example first. I really think that you may have started down the wrong road and it would be worth backing up and doing some review first. For one thing, you probably don't want to be mixing DataTables and LINQ, typically you'd work with strongly-typed models and have your data context/repository return IQueryable/IEnumerables of the model instead of a DataTable. For another, there is a controller method that is able to turn a model into JSON for you. Generally, you should need to write your own JSON serialization.

Declare a list and serialze it into json.
Here Lstcustomeris a genric list of class type customer
I Assign values to class varable and then insert this class in list of Lstcustomer
e.g.
Dim js As New System.Web.Script.Serialization.JavaScriptSerializer
Return js.Serialize(Lstcustomer)

Related

Something akin to "Sparse Fieldsets" in .NET

I'm trying to find the vocabulary to describe what I want and if it exists.
I have a table that shows a few data points from large objects. Loading the entire objects just for the table is very slow. Is there a way to only pass to the front the few properties I want without having to define a new object?
I found something called Sparse Fieldsets in JSON API, and I'm wondering if something like this exists for .NET under another name.
Update:
Talking to another coder, I realize it probably makes more sense to implement something like this between the backend and the database and make a specific call for this table. I still need to work out if I need to create a new object to support this. I think it'd still be faster if I just kept the same object but nulled out all of the connecting objects that I don't need for the table. But maybe that's considered bad practice? Also we're using Entity Framework for what it's worth.
Update 2:
I just created a new query without all of the .Include() and works well enough for what I need:
_dataContext.ApplePie
.Include(f => f.Apples).ThenInclude(f => f.Apple)
.Include(f => f.Sugars).ThenInclude(f => f.MolecularStructure)
.Include(f => f.Recipe)
Maybe you are looking for Anonymous Types?
For example, if you had a typed object with three properties, but you only wanted to operate on two:
var threePropThing = new ThreePropertyThing { Id = 1, Message = "test", ExtraProperty = "ex" };
var myAnonThing = new { Id = threePropThing.Id, Message = threePropThing.Message };
Best practice would be to not pass this anonymous object around. But, if you really needed to, you could return it as type object.
Typically, when passing data around in c#, you want to have it typed.
C# is a strongly-typed language and I would say that it is unusual for C# to support scenarios, when object definition (properties) are not known in advance, like in JSON API "fields" parameter case. Implementing this would imply using reflection to filter the properties, which is usually slow and error-prone.
When implementing C# web-services, people usually create one DTO response model per each request.
If your table has fixed set of fields, I would personally recommend to create a DTO class containing only the fields which are required for your table, and then create a method which returns this response for your specific request. While it doesn't align with "without having to define a new object" in the question, it makes the intention clear and makes it really easier to maintain the API in future.
You might want to use libraries like AutoMapper to save time and avoid duplicated code of copying the values from data model to DTO, if you have many such methods.

MVC & Basic Data Access

I have experience with webForms and now i am starting to learn MVC, oh boy....everything looks so different. Since my background is webForms, I just want to make sure If am doing this properly. I am pulling data (Queries, Stored Procedures etc) from MS SQL Server & Goal is to represent them within view. here is what I have done so sar.
Here is my Model
Class Product ' Just a Template
private _title
private _price
' property implementation etc
End Class
Class ProductModel ' Returns Actual Data
Function getProducts as list(of product)
' use SqlDataReader to Execute the Stored Procedure
' Populate a list(of product)
' list.add(new product(title,price))
' Return the List
end function
Function getTopProducts() as list(of products)
End Function
End Class
Now Here is my ProductsController index() ActionMethod.
Dim p as new ProductModel
return view(p)
Then within my View (Which is strongly typed for ProductModel Class), I am using a For each on Model.getProducts or Model.getTopProducts and showing the data on screen.
Now Few questions...first of all, is my approach reasonable? is it a standard way of setting up Models with MVC? If not then please correct me.
Secondly, all the examples I see online, i see people using LINQ, EF etc....however in my environment performance is very important, and i am almost always returning data using Stored procedures, so is it OK to use pure ADO.NET or using LINQ/EF can help me out in some way?
...is my approach reasonable? is it a standard way of setting up
Models with MVC? If not then please correct me.
Yes, it's best practice to use a viewmodel than work with your entities directly on your views.
is it OK to use pure ADO.NET or using LINQ/EF can help me out in some
way?
It's perfectly fine to use pure ADO.NET if you feel doing all the dirty works an ORM provides.
You approach is the one that is mostly shown when you learn about MVC. However, if you want to be a bit picky about naming convention then your ProductModel would be called ProductViewModel. This ViewModel will allow you to pass more information to View than it is available in your Product class (which is your model class). But this is insignificant although you should get used to using View with ViewModels.
As for your second question you can use anything you want as data access technology. Entity Framework is promoted by Microsoft as one of its technologies for manipulating with the information in a database. However, if you want you can use ADO.NET with stored procedures, or you can use RavenDB with its own client interface. It's really up to you.

How to call stored proc from ASP.Net MVC stack via the ORM & return them in json?

i'm a total newbie with asp.net mvc and here's my jam:
i have a 3 level list box which selection on box A shows options on box B and selection on box B will show the options for box C.
I'm trying to do the whole thing in asp.net MVC and what i see is that the nerd dinner tutorial uses the ORM method.
so i created a dbml to the database and drag the stored proc inside.
i create a datacontext object but i don't quite know how to connect the result from the stored proce which should be multiple rows of data and make it into a json.
so i can keep all the json data inside the html page and using jquery i could make the selection process faster.
i don't expect the data inside the three boxes to change so often thus i think this method should be quite viable.
Questions:
So how do i get the stored proc part
to return the data as json?
i've noticed some tutorial online
that the json return result part is
at the controller and not at the
model end.
Why is that?
Edit
FYI, i find what i mostly wanted to do here.
For the json part, i referenced here.
Return a JsonResult from your controller action. You may need to coerce the result from your stored procedure into a C# class serializable to Json.
Json conversion should be done in the controller because it's not really part of the domain. More a DTO in the MVVM (Model-View-ViewModel) style.

How to use Stored Procedures w/ ASP.NET DataGrid

Question can also be:
What is your preferred way of invoking stored procedures to fill a DataGrid?
I am currently developing an ASP.NET Page, and I would like to know if Linq is the right way to go for use with my SQL Server DB.
ADO seems nice too, so I would just like to have feedback on what is the most appropriate in general terms..
LINQ sure makes it easy to call a stored procedure, but I am kind of stuck in trying to find out the right way to put the result set from the stored procedure to a datagrid.
Don't think I want to do a foreach
there..but all examples seem to point that way.. or I'm just confused
I have read this blog post, and this one, it seems the ways to go are foreach and Ienumerable methods.. and I am a bit confused about the whole thing.
I am also thinking about the tutorial for creating a Movie DataBase where the DataGrid simply became unnecessary in that case.
What is the simplest, most to the
point way of accessing a simple SQL
Procedure and returning a populated datagrid, or datagrid like data presentation model?
I'd suggest using Linq to SQL. You are correct in thinking that you should not be using any foreach loops - all you need is databinding.
eg. In your code behind, you might have a DataBind event that does something like this:
protected void GridView1_DataBanding(object sender, EventArgs e)
{
// Get an instance of our generated DataContext class.
DAL.AdventureWorks db =
new DAL.AdventureWorks(
WebConfigurationManager.ConnectionStrings["AdventureWorksCS"].ConnectionString);
// Get a strongly typed List from the Stored Procedure output
List<DAL.MySPResult> myData = db.MySP().ToList();
GridView1.DataSource = myData;
}
You will need to have setup your Stored Procedure in your Linq to SQL Classes by dragging it onto the design surface.
Hope that helps.
Using a SqlDataSource is the most straightforward way. If you are isolating all of your DB calls in a business layer then you could simply create an ObjectDataSource that called the stored procedure. While it may feel like overkill here, this is a useful skill and very easy to implement once you get the hang of it.
You really don't need LINQ or a foreach, etc. if you'll be using a data-bound control since you won't need to fill it manually (this is what data binding is all about).
One more thing - I would strongly recommend that you use a GridView rather than the DataGrid; it is newer, has many more features automated, and is a more capable and attractive control. Let me know if you need any sample code.

Gridview sorting challenge when moving from Winforms to ASP.NET 2.0 Webforms

I have a problem with Gridview sorting that is similar to others but I'm binding to a collection object as opposed to a data table.
The existing business rules and data access layers of an application follow the pattern of having an object and, if you need a collection of objects of that type, to have another class inheriting CollectionBase and implementing IBindingList.
For desktop applications, it was easy to databind a gridview to one of these objects and there weren't any problems with turning on column sorting. Everything was 'in state' in the desktop app's presentation layer.
Now that code is being moved to a new web application (ASP.NET 2.0, VB codebehind pages).
I've played around with what I had to do to only have certain columns of the collection show up in the gridview and the gridview looked pretty good. When I turned on 'allow sorting', that's when the problems showed up.
I'm getting the error about not having a .Sorting method, etc. In researching this, I found all sorts of solutions that were easily implemented with dataviews if my source was a data table. But it's not - it's a collection. I tried to "cheap shot" a datasource by converting the collection to an XML memory stream and them trying to .ReadXML back into a dataset but that didn't work [Root element is missing error was as far as I got in the dataset.ReadXml(ioTemp) where ioTemp was the System.IO.MemoryStream used in the xml serializer].
Because of the old desktop apps, I've never had to worry about sorting a collection since the gridview handled it once it was loaded. In fact, it's a 'standard' that the collection's .SortProperty, .SortDirection and .ApplySort all through NotSupportedExceptions (I inherited this code from programmers long gone).
Is there an easy way to convert the collection to a data table or a way to sort the collection without having to go back to the database each time? Object Data Sources won't work becuase of the intricate rules in how the objects are built - the wizards in VS2005 just can't handle what we need to do (grabbing data from several tables conditionally to make an object).
Thanks in advance.
Have you considered client side sorting instead?
I have used the jquery tablesorter plugin in the past with ASP Gridviews.
http://tablesorter.com/
I had a similar issue and i needed to implement IComparable on the objects. Basically to sort a collection of objects you need a way to distinguish their order. The IComparable interface has one method called Compare which allows the .Net framework to work out the order of the objects when you sort them. You need to implement this method yourself to get the sort method to work.
Google results
You don't mention the error message so i cant be sure if this is the case, can you post the error?
EDIT :
In regards to your comment; you can implement multi column sorting, it just requires more work. You can specify the fields to sort the collection by and then use this information within the CompareTo Method.
Have a look at this
Given that you apparently are populating the grid with a collection of your own objects, this sounds like a perfect job for Linq for Objects. With just a little elbow grease you can achieve what is effectively an SQL Select statement against your collection. Very cool stuff.
http://www.hookedonlinq.com/LINQtoObjects5MinuteOverview.ashx
Also, do you really just want to sort the data in the grid? If so, then'd definitely pursue using Linq against your objects. However, rarely does sorting the contents of the grid really answer the problem ("sorting the grid" usually translates into changing the access path of the data used to fill the grid.) Browser apps aren't like Windows apps and don't have a full-time connection to the underlying data source to make things happen quite as magically as the DataGridView in Windows makes things seem.
You can put link buttons with an On_Click event as the header's of each column.
When the event is triggered, figure out which header was clicked on (one method per header or a commandArgument value). Once that is know, do a .orderBy or .OrderByDescending by on the collection of objects, and put the result back in as datasource of the gridview and databind on that.
In the year since I originally asked this question, I managed to get a new 'standard' implemented so that collections of business objects were now generic lists.
So now a "Collection class" that is little more than a "Inherits List(Of MyBusinessObject)" with a Sort Method that looks like this (performance wasn't an issue):
Public Overloads Sub Sort(ByVal strPropertyName As String, ByVal strDirection As String)
Dim arSortedList As New ArrayList
For Each item As MyBusinessObject In Me
arSortedList.Add(item)
Next
arSortedList.Sort(New CaseInsensitiveComparer(Of MyBusinessObject)(strPropertyName, strDirection))
For intI As Integer = 0 To arSortedList.Count - 1
Item(intI) = arSortedList(intI)
Next
End Sub
This seemed to work perfectly with the methodology used by the GridView for firing events.

Resources