Checking to see if ViewBag has a property or not,

2019-01-17 14:23发布

Consider this simple controller:

Porduct product = new Product(){
  // Creating a product object;
};
try
{
   productManager.SaveProduct(product);
   return RedirectToAction("List");
}
catch (Exception ex)
{
   ViewBag.ErrorMessage = ex.Message;
   return View("Create", product);
}

Now, in my Create view, I want to check ViewBag object, to see if it has Error property or not. If it has the error property, I need to inject some JavaScript into the page, to show the error message to my user.

I created an extension method to check this:

public static bool Has (this object obj, string propertyName) 
{
    Type type = obj.GetType();
    return type.GetProperty(propertyName) != null;
}

Then, in the Create view, I wrote this line of code:

@if (ViewBag.Has("Error"))
{
    // Injecting JavaScript here
}

However, I get this error:

Cannot perform runtime binding on a null reference

Any idea?

5条回答
啃猪蹄的小仙女
2楼-- · 2019-01-17 15:00

You can use ViewData.ContainsKey("yourkey").

In controller:

ViewBag.IsExist = true;

In view:

if(ViewData.ContainsKey("IsExist")) {...}
查看更多
做个烂人
3楼-- · 2019-01-17 15:02

Instead of using the ViewBag, use ViewData so you can check for the of the item you are storing. The ViewData object is used as Dictionary of objects that you can reference by key, it is not a dynamic as the ViewBag.

// Set the [ViewData][1] in the controller
ViewData["hideSearchForm"] = true;    

// Use the condition in the view
if(Convert.ToBoolean(ViewData["hideSearchForm"])
    hideSearchForm();
查看更多
Root(大扎)
4楼-- · 2019-01-17 15:06

I would avoid ViewBag here completely. See my thoughts here on this: http://completedevelopment.blogspot.com/2011/12/stop-using-viewbag-in-most-places.html

The alternative would be to throw a custom error and catch it. how do you know if the database is down, or if its a business logic save error? in the example above you just catch a single exception, generally there is a better way to catch each exception type, and then a general exception handler for the truly unhandled exceptions such as the built in custom error pages or using ELMAH.

So above, I would instead ModelState.AddModelError() You can then look at these errors (assuming you arent jsut going to use the built in validation) via How do I access the ModelState from within my View (aspx page)?

So please carefully consider displaying a message when you catch 'any' exception.

查看更多
在下西门庆
5楼-- · 2019-01-17 15:11

Your code doesnt work because ViewBag is a dynamic object not a 'real' type.

the following code should work:

public static bool Has (this object obj, string propertyName) 
{
    var dynamic = obj as DynamicObject;
    if(dynamic == null) return false;
    return dynamic.GetDynamicMemberNames().Contains(propertyName);
}
查看更多
Fickle 薄情
6楼-- · 2019-01-17 15:13
@if (ViewBag.Error!=null)
{
    // Injecting JavaScript here
}
查看更多
登录 后发表回答