How do I populate a view model with static data - c#

I have a Controller that I am using to pass a list of JSON data to my view. Currently I'm using Linq to Entities to populate the Viewmodel now but since it is a static list of only 15 pairs, I want to hard code the Viewmodel but I'm not sure how to do that. Here is my Controller
public JsonResult GetSites()
{
var sites = context.vAaiomsSites.Select(s => new vAaiomsSitesVM
{
ID = s.ID,
SiteName = s.SiteName
}).OrderBy(s => s.SiteName);
return Json(sites, JsonRequestBehavior.AllowGet);
}
I just need an array like this:
SiteID: 1, SiteName : Barter Island
SiteID: 2, SiteName: Cape Lisburne
....12 more times.

Use collection initializer to create an array (or List<T>) of the ViewModels:
public JsonResult GetSites()
{
var sitesArray = new vAaiomsSitesVM[]
{
new vAaiomsSitesVM
{
ID = 1,
SiteName = "Barter Island"
},
new vAaiomsSitesVM
{
ID = 2,
SiteName = "Cape Lisburne"
}
// And so on...
};
var sites = sitesArray.OrderBy(s => s.SiteName);
return Json(sites, JsonRequestBehavior.AllowGet);
}

If you really want to hardcode it, you can do it like this.
Create a class for your ViewModel
public class Site
{
public int SiteID { set;get;}
public string SiteName { set;get;}
}
and in your Action method
public JsonResult GetSites()
{
var list=new List<Site>();
list.Add(new Site{ SiteID=1, SiteName="SiteName 1" } );
list.Add(new Site{ SiteID=2, SiteName="SiteName 2" } );
//13 more times !!!!
return Json(list, JsonRequestBehavior.AllowGet);
}
But Why do you want to HardCode it ? I recommend you to avoid this if at possible.If you are worried about querying your database everytime, you may think about storing the data in a middle Caching Layer and fetch it from there thus avoiding call to database. Think twice.

Related

ASP.NET Core web application - display database data C#

I'm trying to display data from a SQL Server database. I've been struggling with it for a whole day now and still can't find any working solution or tutorial.
What I want to do - make a simple "database browser". The best thing that worked so far was this tutorial https://www.c-sharpcorner.com/article/entity-framework-database-first-in-asp-net-core2/
But I have only one table to display and I don't know how to write this part of code:
public IActionResult Index()
{
var _emplst = _dbContext.tblEmployees
.Join(_dbContext.tblSkills, e => e.SkillID, s => s.SkillID,
(e, s) => new EmployeeViewModel
{ EmployeeID = e.EmployeeID, EmployeeName = e.EmployeeName,
PhoneNumber = e.PhoneNumber, Skill = s.Title,
YearsExperience = e.YearsExperience }).ToList();
IList<EmployeeViewModel> emplst = _emplst;
return View(emplst);
}
for just one table (without any join). Everything I try ends up with an error that I cannot convert tblEmployees to EmployeeViewModel.
Could someone possibly help me? Or suggest any other solution, that might work? I really just want to drag a data from a table and display it on a web page.
EDIT:
ComponentContext.cs:
public class ComponentsContext:DbContext
{
public ComponentsContext(DbContextOptions<ComponentsContext> options) : base(options)
{
}
public DbSet<tblComponents> tblComponent { get; set; }
}
}
Your _emplst list is of a different type (class) than the type (class) EmployeeViewModel.
So you need to go through you list _emplst and transfer the values needed in EmployeeViewModel.
This can be something like this:
public IActionResult Index()
{
var _emplst = _dbContext.tblEmployees.
Join(_dbContext.tblSkills, e => e.SkillID, s => s.SkillID,
(e, s) => new EmployeeViewModel
{ EmployeeID = e.EmployeeID, EmployeeName = e.EmployeeName,
PhoneNumber = e.PhoneNumber, Skill = s.Title,
YearsExperience = e.YearsExperience }).ToList();
var emplst = _emplst.Select( e=> new EmployeeViewModel {
.. i dont known the properties ..
A = e.A,
B = e.B,
... ..
}).ToList();
return View(emplst);
}
As answer to your comment below on the tlbComponent, try this:
var _cmplist = _dbContext.tblComponent.ToList().Select(e => new ComponentsViewModel { ID = e.ID, Name = e.Name, } ).ToList();
IList<ComponentsViewModel> cmplist = _cmplist;
return View(cmplist);
i have change _dbContext.tblComponent.Select(... to _dbContext.tblComponent.ToList().Select(....

Kendo Grid changing depending on DropDownList

Before I start I'll just say that I've looked at other answers before posting and none specifically help me.
I need to create a Kendo UI grid in ASP.NET MVC that changes depending on what the users selects from a DropDownList. I will eventually be using data from a database, but currently I'm trying to learn with random hard-coded data.
I found a tutorial online that shows me how to do it with data from a sample database, but I can't set that up for reasons I cant explain. So I'm trying to adapt the code from that tutorial to work with my controllers and models. This might be set up completely wrong as I'm relatively new to ASP.NET MVC.
So here's the tutorial I'm trying to follow.
This is my controller:
public class LookupValueController : Controller
{
private List<LookupModel> tables = new
List<LookupModel>()
{ new LookupModel() { TableName = "Table1",
Description = "Table 1" },
new LookupModel() { TableName = "Table2",
Description = "Table 2" } };
private List<LookupValueModel> values = new List<LookupValueModel>()
{ new LookupValueModel() { TableName = "Table1", Description = "Value 1", LookupCode = "1" },
new LookupValueModel() { TableName = "Table2", Description = "Value 2", LookupCode = "2"} };
// GET: LookupValue
public ActionResult Index()
{
return View();
}
public ActionResult GetAllTableA()
{
try
{
var table = tables;
return Json(table, JsonRequestBehavior.AllowGet);
}
catch (Exception ex)
{
return Json(ex.Message);
}
}
public ActionResult GetAllTableB()
{
try
{
var value = values;
return Json(value, JsonRequestBehavior.AllowGet);
}
catch (Exception ex)
{
return Json(ex.Message);
}
}
}
Then my 2 models:
public class LookupValueModel
{
public string TableName { get; set; }
public string LookupCode { get; set; }
public string Description { get; set; }
}
public class LookupModel
{
public string TableName { get; set; }
public string Description { get; set; }
}
I've tried just changing the values in the view in the tutorial but it doesn't work, as I believe it isn't as simple as just changing some text.
I'm pretty stuck for how to do this and don't know where to go from here. I know this is a very long winded post with lots of code, but I would really appreciate some help.
Where am I going wrong adapting the tutorial code? What do I have to change to get it to work with hard-coded data?
That's not that hard. What you need to do is to change the DataSource's url for each Action you want. So, depending on what options user selects in the DDL, you change the DataSource. Check this demo.
What you need to change in from the above demo is that your grid's DataSource will call an url instead of a hard-coded json, right? In that url, you change the desired action:
let changeTableData = function changeTableData(option) {
let dataSource = new kendo.data.DataSource({
transport: {
url: "MyApp/" + option
}
});
$("#grid").data("kendoGrid").setDataSource(dataSource);
};
It will read the new url and fetch the data into the grid and updated it.
UPDATE
The transport url ir the url path to your action, e.g.
let url;
if (option == "A") {
url = "#Url.Action("TableA")";
}
else if (option == "B") {
url = "#Url.Action("TableB")";
}
let dataSource = new kendo.data.DataSource({
transport: {
url: url
}
});
1) Remove the grid from this view and create a new partialview and just have the grid located in that.
Now this can be one of two ways. Either an onclick via the drop down list or an onchange. Your choice
function Getdropdown()
{
var id = $("#//dropdownID").val(); //Get the dropdown value
var json = '{dropdownId: ' + id + '}';
$.ajax({
url:'#Url.Action("ViewGrid", "//Controller")',
type:'POST',
data:json,
contentType:'Application/json',
success:function(result){
$("//The Id of of the div you want the partial to be displayed in in the cshtml").html(result);
}
});
}
2) Get the value of the dropdown and pass it to a controller method that calls this new partial view, sending it the ID in a model
public ActionResult ViewGrid(int dropdownId)
{
AModel model = new AModel
{
DropDownID = dropdownId
};
return PartialView("_theGridPartial", model);
}
3) Change your grid to look like this:
#(Html.Kendo().Grid<KendoMvcApp.Models.EmployeeA>()
.Name("EmpGrid")
.Selectable()
.Columns(columns =>
{
columns.Bound(c => c.FirstName);
columns.Bound(c => c.LastName);
})
.DataSource(dataSource => dataSource
.Ajax()
.Read(read => read.Action("GetAllEmployee", "GridDataSource", new {id = Model.DropDownID}))
)
)
4) This is the new Controller read
public ActionResult GetAllEmployee([DataSourceRequest]DataSourceRequest request, int id)
{
try
{
//Have a call that gets the table data based on the id you are passing into here. This id will be the table id you have got from your dropdown list
}
catch (Exception ex)
{
return Json(ex.Message);
}
}
This should allow you to change the table based on the dropdown.

Return Entity Framework Objects as JSON

I try to return Entity Framework Objects as Json with the following method in my Controller:
public JsonResult EventList() {
var results = from s in db.Events
select new
{
OrderID = s.EventID,
OrderTitle =s.EventType,
OrderDate = s.Title
};
return Json(results);
}
I get a server error 500 when entering the page /events/EventList/. Also a Jquery get request returns no data. What is the correct way to return the results in Json format?
Update:
This seems to work. But I need results from the database.
public ActionResult EventList() {
Event test = new Event
{
EventID = 1,
Title = "test",
Description = "test"
};
return Json(new { event = test }, JsonRequestBehavior.AllowGet);
}
Edit: 2019
This answer still gets upvotes - if you're going down this road I really really suggest you just save yourself the future headaches and use a DTO. Serializing your entity is probably faster for now but (and I have learned this the hard way) - you are going to hate yourself in a years time.
New answer - updated for 2018:
The original answer below will work every time and if you're using lazy loading, it may still be the best solution. Without lazy loading though, you can do the following with Newtonsoft.JSON:
var settings = new JsonSerializerSettings()
{
ReferenceLoopHandling = ReferenceLoopHandling.Ignore,
Error = (sender, args) =>
{
args.ErrorContext.Handled = true;
},
};
using(var context = new myContext())
{
var myEntity = myContext.Foos.First();
return JsonConvert.SerializeObject(myEntity, settings);
}
Which basically will serialize anything that's been included in the entity framework request, while ignoring any errors and reference loops.
The drawback to this method is that controlling what gets serialized is harder and if you're performance conscious, you may need to start decorating your generated Entity Framework classes with a pattern like
// a new partial class extending the Foo generated class, allowing us to apply an interface
[MetadataType(typeof(IFooMetaData))]
public partial class Foo : IFooMetaData
{
}
// meta data interface, forcing json ignore on Foo.Bars
public interface IFooMetaData
{
[JsonIgnore]
ICollection<Bar> Bars {get;set;}
}
Original answer - 2015:
Can get this response:
[
{
"OrderID": 1
},
{
"OrderID": 2
},
{
"OrderID": 3
}
]
from this:
public JsonResult Test()
{
var events = new List<Event>()
{
new Event() {EventId = 1},
new Event() {EventId = 2},
new Event() {EventId = 3}
};
var results = events.Select(e => new
{
OrderID = e.EventId
}).ToList();
return new JsonResult() { Data = results, JsonRequestBehavior = JsonRequestBehavior.AllowGet };
}
So yours should be something like
public JsonResult Test()
{
var results = db.Events.Select(e => new
{
OrderID = e.EventId
}).ToList();
return new JsonResult() { Data = results, JsonRequestBehavior = JsonRequestBehavior.AllowGet };
}
edit
re-posted with tested code
In the controller:
for example
List<categories> data = context.categories.toList(); //to here all right
now, the problem with the serialization for "data" for send the json result...
i just used a struct to replace the List how???
just watch:
in the same controller ...
struct categories_struct{
public fieldname {get;set;}
//the same for others firelds (same the model)
}
now, in the ActionResult or maybe in jsonresult :
List<categorias> data = contexto.categorias.ToList(); //I use the EF
List<catego> data2 = new List<catego>(); //create the struct var
foreach (categorias item in data) //fill the struct with data
{
catego item2 = new catego();
item2.codcat = item.codcat;
item2.nomcat = item.nombrecat;
item2.descripcion = item.descripcion;
data2.Add(item2);
}
//here, Data contains all data2
return Json(new { Data = data2 }, JsonRequestBehavior.AllowGet);
in the view:
$.ajax({
url: "/Categorias/getTabla",
dataType: "JSON",
type: "POST",
}).done(function (respuesta) {
var data = JSON.parse(JSON.stringify(respuesta));
console.log(respuesta);
alert('exito');
}).fail(function () {
alert('oh no, again!');
});
///
is my solution for this problem

How to get value from IEnumerable collection using its Key?

I have IEnumerable collection like following
IEnumerable<Customer> items = new Customer[]
{
new Customer { Name = "test1", Id = 999 },
new Customer { Name = "test2", Id = 989 }
};
I want to get value using key Id
I tried like following
public int GetValue(IEnumerable<T> items,string propertyName)
{
for (int i = 0; i < items.Count(); i++)
{
(typeof(T).GetType().GetProperty(propertyName).GetValue(typeof(T), null));
// I will pass propertyName as Id and want all Id propperty values
// from items collection one by one.
}
}
If you want to retrieve a Customer name from a collection by its Id:
public string GetCustomerName(IEnumerable<Customer> customers, int id)
{
return customers.First(c => c.Id == id).Name;
}
Using LINQ you can get all customers names (values) having specific value in this way:
var valuesList = items.Where(x => x.Something == myVar).Select(v => v.Name).ToList();
For single customer name you can do this:
var singleName = items.FirstOrDefault(x => x.Id == 1)?.Name;
Obviously, the Id can be 1, 2 or any other.
Edit:
I recommend you List<Customer> instead of Customer[]
So,
var items = new List<Customer>
{
new Customer { Name = "test1", Id = 999 },
new Customer { Name = "test2", Id = 989 }
};
// I will pass propertyName as Id and want all Id propperty values
// from items collection one by one.
If I understand you correctly
public static IEnumerable<object> GetValues<T>(IEnumerable<T> items, string propertyName)
{
Type type = typeof(T);
var prop = type.GetProperty(propertyName);
foreach (var item in items)
yield return prop.GetValue(item, null);
}
Just use LINQ to achieve what you want to do. if you want to retrieve a specific value you can use where like this:
public Customer GetCustomerById(IEnumerable<Customer> items,int key)
{
return items.Where(x=>x.id==key)
.Select(x =>x.Name)
.First();
}
this will retrieve the customer who match a specific Id.
Do you want to look things up repeatedly after creating the list? If so, you might want to consider creating a dictionary to do the lookups, like so:
IEnumerable<Customer> items = new Customer[]
{
new Customer {Name = "test1", Id = 999},
new Customer {Name = "test2", Id = 989}
};
var lookup = items.ToDictionary(itemKeySelector => itemKeySelector.Id);
var result = lookup[989];
Console.WriteLine(result.Name); // Prints "test2".
I'm assuming that you don't create the collection in the first place - if you had control over creating the original collection you could use a dictionary in the first place.
private TextBox [] Collectionstextboxonpanel(Panel panel)
{
var textBoxspanel1 = panel.Controls.OfType<TextBox>(); // select controls on panle1 by type
IEnumerable<TextBox> textBoxes = textBoxspanel1; // create collection if need
TextBox[] textBoxes1 = textBoxes.ToArray(); // Array collection
return textBoxes1; // get back TextBox Collection
}

MongoCollection<T> to Collection<T>

I have a class called Employee. From my controller i am passing IEnumerable<Employee> to view. How to convert MongoDB.Driver.MongoCollection<Employee> to IEnumerable<Employee>?
public ActionResult Index()
{
var server = MongoServer.Create("mongodb://127.0.0.1");
var db = server.GetDatabase("employee");
var employeeCollection = new Collection<Employee>
{
new Employee
{
EmployeeId = new ObjectId(),
EmployeeName = "A"
},
new Employee
{
EmployeeId = new ObjectId(),
EmployeeName = "B"
}
};
var collection = db.GetCollection<Employee>("employee");
collection.InsertBatch(employeeCollection);
return View(collection);
}
You can just use FindAll and that will allow you to enumerate over the entire collection:
return View(collection.FindAll());
You could also use AsQueryable to achieve the same result:
return View(collection.AsQueryable());
But you should be careful about doing that. The collection could possibly contain millions of documents.

Categories

Resources