I have deserialized my JSON response into an object. What are the next steps? I have a WebAPI controller that I currently working with my JSON object. I need to take this data and move it into a view so that I can connect it to my web components.
I guess I'm confused on if I should iterate through my JSON object in the controller or in the view? I have the following:
var model = JsonConvert.DeserializeObject<MyData.RootObject>(Data);
foreach (var record in Data.rows)
{
foreach (var nestedRecord in record.f)
{
List<string> list = new List<string>();
list.Add(nestedRecord.v);
}
}
return View();
Also, I'm iterating through this model and I cannot return the model in the view since it's outside the scope.
I see two popular options here, depending on how much information you might potentially access from the deserialized object. One, use the MyData.RootObject as your model, and iterate it in the view. This would give you the greatest flexibility if you need to access other properties of the object:
var model = JsonConvert.DeserializeObject<MyData.RootObject>(Data);
return View(model);
In the view (this unordered-list markup is only a sample), you might have:
#model MyData.RootObject
<ul>
#foreach (var record in Model.rows)
{
foreach (var nestedRecord in record.f)
{
<li>#nestedRecord.v</li>
}
}
</ul>
Or, continue as you had planned, but move the list you're populating outside of the for-loops, using the list as the model. This would be the least flexible in terms of rendering your object in the view:
var rootObject = JsonConvert.DeserializeObject<MyData.RootObject>(Data);
List<string> list = new List<string>();
foreach (var record in rootObject.rows)
{
foreach (var nestedRecord in record.f)
{
list.Add(nestedRecord.v);
}
}
return View(list);
And your view in this case (much more concise than the other option):
#model System.Collections.Generic.List<string>
<ul>
#foreach (var record in Model)
{
<li>#record</li>
}
</ul>
Related
I am new to C# and Umbraco. Can't figured this simple thing out nor find the solutions
#inherits Umbraco.Web.Mvc.UmbracoTemplatePage
#{
Layout = null;
}
List<string> test = new List<string>();
var item = CurrentPage.Children.FirstOrDefault();
var count = 0;
foreach (var prop in item.Properties) {
count++;
test.Add(prop.PropertyTypeAlias);
}
<html>
...
</html>
If i count properties it gives correct number of properties but i can't get access its own properties such as "Value", "PropertyTypeAlias" etc. It throw exception reads:
Microsoft.CSharp.RuntimeBinder.RuntimeBinderException: 'object' does not contain a definition for 'PropertyTypeAlias'
Thanks in advance.
If you want to access properties of a document type, it's better and easier to do it like this:
#inherits UmbracoTemplatePage
#{
}
<h1>#Model.Content.Name</h1>
#foreach (var item in Model.Content.Children)
{
<h2>#(item.GetPropertyValue<IHtmlString>("bodyText"))</h2>
}
CurrentPage is a dynamic object, whereas Model.Content gets the "current page", but as a strongly-typed IPublishedContent, which means, if you use Visual Studio, you get intellisense and can see which methods you can use.
In the H1-tag, I simply pulled out the current content node's name, in the foreach, I am looping over the current content node's children and displaying their property with alias "bodyText" and datatype "Rich text".
EDIT:
#inherits UmbracoTemplatePage
#{
var child = Model.Content.Children.FirstOrDefault();
var properties = new List<string>();
foreach (var item in child.Properties)
{
properties.Add(item.PropertyTypeAlias);
}
}
#foreach (var item in properties)
{
<h1>#item</h1>
}
Using the ReleatedEntity I already get a list of the related entities. But I only want to stick the Id+Name in a viewbag so that Razor can bind the dropdown.
Question:
How to get only Id, Name of Entity as a List so that I can bind it to DropDowns in ASP MVC 5 in razor*; and put it as Viewbag.Attribute, i.e. ViewBag.EntityName
Edit 1: Simplified my code
foreach (var relatedFkEntity in (((IEntityWithRelationships)EntityType.FirstOrDefault())
.RelationshipManager.GetAllRelatedEnds()))
{
// EntityNameHere <- how to stick the Id and Names list there from the EF entities
viewbag.**Entity Name Here** = dropdownListWithId&Name; //??
entity.Include(relatedEntity.TargetRoleName).ToList();
}
Could you please have a look following code, please make changes this has not been tested
foreach (var relatedFkEntity in (((IEntityWithRelationships)EntityType.FirstOrDefault ()).RelationshipManager.GetAllRelatedEnds()))
{
viewbag.drpList = new SelectList(entity.Include(relatedEntity.TargetRoleName).ToList(), "Id", "Name");
}
I want to display records of different entities relating to a single entity.
A tenant for example has a collection of rents, rents in turn have collection of payments.
I want to display in the view, all tenants with the rents and payments.
Here is my current implementation in my view.
#foreach (var t in Model.Tenants)
{
<tr>
<td>#t.Fullname</td>
#foreach (var rents in t.Rents)
{
<td>#rents.Apartment.BedroomType</td>
<td>#rents.Apartment.MonthlyFee.ToString("N0")</td>
<td>#($"{#rents.Total.ToString("N0")}/{#rents.Type}")</td>
<td>#($"{#rents.DueDate.ToString("MMM yyy")}")</td>
foreach (var payments in rents.Payments)
{
<td>#payments.PaymentDate.ToString("MMM dd,yyyy")</td>
<td>#payments.AmountPaid.ToString("N0")</td>
<td>#payments.Balance</td>
}
}
</tr>
}
This currently works fine but I don't want to be doing lots of filtering on the client which I think its not a good practice, so I want to move the logic to my controller to handle all filtering of records.
What I want to do is change this implementation using a list and add each collection into its own list. Payments for instance would be in its own list relating to its rent. Rents would be in its own list relating to the specific tenant. By doing this I can maybe filter rents based on rental status or only show payments that have been actually paid. This current implementation does not give me that.
I could really use some help with guidelines here...
I would say you just need to make a small change. In your view model, have a list of payments instead of tenants (do it the other way round). Have a look at the example below for an idea of what I mean:
[HttpGet]
public ActionResult Index(string bedRoomType = "", double amountPaid = 0)
{
var viewModel = new TenantIndexVm();
using (var context = new RentEntities())
{
viewModel.Payments = context.Payment.Where(x => (x.Rent.BedRoomType == bedRoomType || bedRoomType == "") && (x.AmountPaid >= amountPaid)).Include("Rent.Tenant");
}
return View(viewModel);
}
In the view, you would loop through the payments:
#foreach (var p in Model.Payments)
{
<tr>
<td>#p.Rent.Tenant.Fullname</td>
<td>#p.Rent.Apartment.BedroomType</td>
<td>#p.Rent.Apartment.MonthlyFee.ToString("N0")</td>
<td>#($"{#p.Rent.Total.ToString("N0")}/{#p.Rent.Type}")</td>
<td>#($"{#p.Rent.DueDate.ToString("MMM yyy")}")</td>
<td>#p.PaymentDate.ToString("MMM dd,yyyy")</td>
<td>#p.AmountPaid.ToString("N0")</td>
<td>#p.Balance</td>
</tr>
}
My controller code is as follows
ViewBag.Districts = (from a in _dbContext.DISTRICTS
select new ComboItem {
ID = a.DISTRICT_ID,
Name = a.DISTRICT_NAME
}
).ToList();
My Razor View code as follows
#foreach (var dist in ViewBag.Districts)
{
if (item.DISTRICT_ID == dist.ID)
{
#dist.Name
}
}
Is there a way I can find item in ViewBag.Districts like ViewBag.Districts.where(m=>m.ID==item.DISTRICT_ID.
or linq expression so that i can avoid looping.
Anyone helps me greatly appreciated.
Viewbag is dynamic so compiler won't be able to identify its actual Type, so you need explicit type cast like this to work with Enumerable methods:-
((IEnumerable<ComboItem>)ViewBag.Districts).Where(x => x.ID == item.DISTRICT_ID);
I am assuming you want to use this in your View, Also the foreach loop you have posted won't work without explicit casting:-
#foreach (var dist in (IEnumerable<ComboItem>)ViewBag.Districts)
{
if (item.DISTRICT_ID == dist.ID)
{
#dist.Name
}
}
I can't find anything to solve my problem in search, and here is my problem:
I'm using ASP.NET MVC 4 and EF 5, I'm trying to get a value from my db, but this db field depends on other var.
In Controller:
public ActionResult Products()
{
ViewBag.lang = "ENG";
DataEntities db = new DataEntities();
ViewBag.Categories = db.Categories;
return View();
}
In Template View:
<ul>
#{
if (ViewBag.Categories != null)
{
foreach (var cat in ViewBag.Categories )
{
<!-- we need in this case "Name_ENG" -->
var title = "Name_" + #ViewBag.lang;
<li>#cat.(title)</li>
<!-- out: cat.ToString() + "(title)" -->
<li>#cat.(#title)</li>
<!-- out: cat.ToString() + "(" + title.ToString() + ")" -->
<li>#cat.#title</li>
<!-- out: cat.ToString() + title.ToString() -->
}
}
}
</ul>
is there a way to get property "Name_ENG" from cat object like #cat.Name_ENG using a string ?
"In this case I'm trying to list al Categories in Products page."
Thanks a lot
No, definitely not in c#. You'd have to use reflection for this to work (and the syntax would be different of course as well).
I think a better option would be to create a method that would retrieve the value based on a string input, like
public T GetValue<T>(string propertyName)
and call that from your view when needed
here is an article from msdn. You can access EF entries properties by name. But at first you need dbContext and second it is wrong to access dbContext from view.
example:
object currentName2 = context.Entry(blog).Property("Name").CurrentValue;
Also, as mentioned in another answer, reflection:
object value = typeof(YourType).GetProperty("PropertyName").GetValue(yourInstance, null);
Try this
<ul>
#{
if (ViewBag.Categories != null)
{
foreach (var cat in ViewBag.Categories )
{
// here you can do something on cat
<text>
<li>#(cat.title)</li>
</text>
}
}
}
</ul>
I personally suggest you to pass the data to the view by parameter. And use #model in the view (strong type view).