7

I am trying to pass data from controller to view. I have searched the web but could not find a solution.

if I do this it works:

Controller:

var yyy = (from a in Connection.Db.Authorities select a) ;
ViewBag.data = yyy;

View:

@foreach(var item in ViewBag.data)
{
    @item.Value
}

But the following code does not work:

Controller:

var yyy = (from a in Connection.Db.Authorities select new {Value = a.Value, TypeCode = a.TypeCode, Return = Calculate(a.Return)}) ;
ViewBag.data = yyy;

View:

@foreach(var item in ViewBag.data)
{
    @item.Value
}

It gives "item does not contain a definition for Value" for the view file.

Any help would be great.

Thank you.

-edited: updated the second controller linq query. and corrected the first controller linq query.

2
  • Actually, I don't understand why your first code works. That looks like it's displaying a.Value.Value for each a. Commented May 28, 2013 at 13:53
  • @justin you are right, first code does not work. updating now... Commented May 28, 2013 at 14:10

2 Answers 2

5

It's because You already select Value and Value has no such property as Value. You should change in controller:

var yyy = (from a in Connection.Db.Authorities select a.Value); to

var yyy = (from a in Connection.Db.Authorities select a);

OR change the view to

@foreach(var item in ViewBag.data)
{
    @item
}

//////////////////////////////////////////////// EDITS ////////////////////////////////////////////////
Than You should not use anonymous object. You should create ViewModelClass. For Example:

public class AuthoritiesViewModel
        {
            public string Value { get; set; }
            public string TypeCode { get; set; }
            public string Return { get; set; }
        }

And change your controller:

var yyy = (from a in Connection.Db.Authorities select new AuthoritiesViewModel{ Value = a.Value, TypeCode = a.TypeCode, Return = Calculate(a.Return)});
ViewBag.data = yyy;

and in your view you will be able to use:

<table>
    <tr>
         <th>Value</th>
         <th>TypeCode</th>
         <th>Return</th>
    </tr>
@foreach(AuthoritiesViewModel item in ViewBag.data)
{
    <tr>
         <td>@item.Value<td>
         <td>@item.TypeCode<td>
         <td>@item.Return<td>
    </tr>
}
</table>

Also, I have a question to You. Why do You use ViewBag to pass data from controller to view? Why don't You use Model to pass these data to view according to MVC pattern?

//////////////////////////////////////////////// MORE EDITS ////////////////////////////////////////////////
To send more than one query result You can create more complex model. For example:

public class AuthoritiesViewModel
        {
            public string Value { get; set; }
            public string TypeCode { get; set; }
            public string Return { get; set; }
        }

        public class AnotherQueryViewModel
        {
            public string AnotherQueryValue { get; set; }
            public string AnotherQueryTypeCode { get; set; }
            public string AnotherQueryReturn { get; set; }
        }

        public class ModelClass
        {
            IEnumerable<AuthoritiesViewModel> Authorities { get; set; }
            IEnumerable<AnotherQueryViewModel> AnotherQueryResults { get; set; }
        }

And change the controller:

var yyy = (from a in Connection.Db.Authorities select new AuthoritiesViewModel{ Value = a.Value, TypeCode = a.TypeCode, Return = Calculate(a.Return)});

// do your another select
var zzz = (from smthing select new AnotherQueryViewModel ...)

// create model instance
ModelClass model = new ModelClass() 
{
    Authorities = yyy.AsEnumerable(),
    AnotherQueryResults = zzz..AsEnumerable()
}

// return view with model
return View("view", model);

and in view you can use:

@model ModelClass

@*display first query result*@
<table>
    <tr>
         <th>Value</th>
         <th>TypeCode</th>
         <th>Return</th>
    </tr>
@foreach(AuthoritiesViewModel item in Model.Authorities)
{
    <tr>
         <td>@item.Value<td>
         <td>@item.TypeCode<td>
         <td>@item.Return<td>
    </tr>
}
</table>

@*display second query result*@
<table>
    <tr>
         <th>Another Query Value</th>
         <th>Another Query TypeCode</th>
         <th>Another Query Return</th>
    </tr>
@foreach(AnotherQueryViewModel item in Model.AnotherQueryResults)
{
    <tr>
         <td>@item.AnotherQueryValue<td>
         <td>@item.AnotherQueryTypeCode<td>
         <td>@item.AnotherQueryReturn<td>
    </tr>
}
</table>
Sign up to request clarification or add additional context in comments.

4 Comments

Actually I want to write the following linq query, select more than 1 field: from a in Connection.Db.Authorities select new { Value = a.Value, TypeCode = a.TypeCode, Return = Calculate(a.Return) }
Yes Dmytro, you are right, it works now. Thank you a lot... The problem is, as you have said, I should create a viewmodelclass. And, as an answer to your question, I want to send more than one query result to view, so I am using ViewBag instead of Model.
@isa, To send more than one query result You can create more complex model. For example see my more edits.
this is exactly what I have been looking for. Thank you very much. You clearly defined everything needed.
0

use sth like this

ViewBag.qualification = new SelectList(db.Lookups.Where(x => x.lookup_type == "Qualification"), "lookup_content", "lookup_content");

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.