title: Alert messages from controller: Add alert behavior in partial view?
body: <p>In MVC 4, you could install this package <a href="https://github.com/erichexter/twitter.bootstrap.mvc" rel="nofollow noreferrer">Twitter.bootstrap.mvc</a> and this would add lots of HTML helpers.</p>
  <p>Once istalled you could send alert to view right from controller.</p>
  <p>For example:</p>
  <pre><code>public class AccountController : BaseController 
  {
      public ActionResult AlertExample()
      {
         Success(&quot;This is a success alert&quot;);
         Error(&quot;This is error alert&quot;);
         Information(&quot;This is information alert&quot;);
         ...
         etc.
      }
  }
  </code></pre>
  <p>This would send the success alert right from controller to the view.</p>
  <p><strong>Objective: Sending Growl Messages from controller</strong></p>
  <p>I've tried to implement same thing from the project I mentioned.</p>
  <p>So, this is what I've added to my project.</p>
  <p><strong>Base controller that other controller derives from</strong></p>
  <pre><code>   public class BaseController : Controller
     {
          //
          // GET: /Base/
          public void Warning(string message)
          {
              TempData.Add(Alerts.WARNING, message);
          }
          public void Success(string message)
          {
              TempData.Add(Alerts.SUCCESS, message);
          }
  
          public void Information(string message)
          {
              TempData.Add(Alerts.INFORMATION, message);
          }
  
          public void Error(string message)
          {
              TempData.Add(Alerts.ERROR, message);
          }
      }
  </code></pre>
  <p><strong>ControlGroupExtensionClass</strong></p>
  <pre><code>    namespace BootstrapSupport
      {
          public class ControlGroup : IDisposable
          {
              private readonly HtmlHelper _html;
      
              public ControlGroup(HtmlHelper html)
              {
                  _html = html;
              }
      
              public void Dispose()
              {
                  _html.ViewContext.Writer.Write(_html.EndControlGroup());
              }
          }
      
      public static class ControlGroupExtensions
      {
          public static IHtmlString BeginControlGroupFor&lt;T&gt;(this HtmlHelper&lt;T&gt; html, Expression&lt;Func&lt;T, object&gt;&gt; modelProperty)
          {
              return BeginControlGroupFor(html, modelProperty, null);
          }
  
          public static IHtmlString BeginControlGroupFor&lt;T&gt;(this HtmlHelper&lt;T&gt; html, Expression&lt;Func&lt;T, object&gt;&gt; modelProperty, object htmlAttributes)
          {
              return BeginControlGroupFor(html, modelProperty,
                                          HtmlHelper.AnonymousObjectToHtmlAttributes(htmlAttributes));
          }
  
          public static IHtmlString BeginControlGroupFor&lt;T&gt;(this HtmlHelper&lt;T&gt; html, Expression&lt;Func&lt;T, object&gt;&gt; modelProperty, IDictionary&lt;string, object&gt; htmlAttributes)
          {
              string propertyName = ExpressionHelper.GetExpressionText(modelProperty);
              return BeginControlGroupFor(html, propertyName, null);
          }
  
          public static IHtmlString BeginControlGroupFor&lt;T&gt;(this HtmlHelper&lt;T&gt; html, string propertyName)
          {
              return BeginControlGroupFor(html, propertyName, null);
          }
  
          public static IHtmlString BeginControlGroupFor&lt;T&gt;(this HtmlHelper&lt;T&gt; html, string propertyName, object htmlAttributes)
          {
              return BeginControlGroupFor(html, propertyName, HtmlHelper.AnonymousObjectToHtmlAttributes(htmlAttributes));
          }
  
          public static IHtmlString BeginControlGroupFor&lt;T&gt;(this HtmlHelper&lt;T&gt; html, string propertyName, IDictionary&lt;string, object&gt; htmlAttributes)
          {
              var controlGroupWrapper = new TagBuilder(&quot;div&quot;);
              controlGroupWrapper.MergeAttributes(htmlAttributes);
              controlGroupWrapper.AddCssClass(&quot;control-group&quot;);
              string partialFieldName = propertyName;
              string fullHtmlFieldName =
                  html.ViewContext.ViewData.TemplateInfo.GetFullHtmlFieldName(partialFieldName);
              if (!html.ViewData.ModelState.IsValidField(fullHtmlFieldName))
              {
                  controlGroupWrapper.AddCssClass(&quot;error&quot;);
              }
              string openingTag = controlGroupWrapper.ToString(TagRenderMode.StartTag);
              return MvcHtmlString.Create(openingTag);
          }
  
          public static IHtmlString EndControlGroup(this HtmlHelper html)
          {
              return MvcHtmlString.Create(&quot;&lt;/div&gt;&quot;);
          }
  
          public static ControlGroup ControlGroupFor&lt;T&gt;(this HtmlHelper&lt;T&gt; html, Expression&lt;Func&lt;T, object&gt;&gt; modelProperty)
          {
              return ControlGroupFor(html, modelProperty, null);
          }
  
          public static ControlGroup ControlGroupFor&lt;T&gt;(this HtmlHelper&lt;T&gt; html, Expression&lt;Func&lt;T, object&gt;&gt; modelProperty, object htmlAttributes)
          {
              string propertyName = ExpressionHelper.GetExpressionText(modelProperty);
              return ControlGroupFor(html, propertyName, HtmlHelper.AnonymousObjectToHtmlAttributes(htmlAttributes));
          }
  
          public static ControlGroup ControlGroupFor&lt;T&gt;(this HtmlHelper&lt;T&gt; html, string propertyName)
          {
              return ControlGroupFor(html, propertyName, null);
          }
  
          public static ControlGroup ControlGroupFor&lt;T&gt;(this HtmlHelper&lt;T&gt; html, string propertyName, object htmlAttributes)
          {
              return ControlGroupFor(html, propertyName, HtmlHelper.AnonymousObjectToHtmlAttributes(htmlAttributes));
          }
  
          public static ControlGroup ControlGroupFor&lt;T&gt;(this HtmlHelper&lt;T&gt; html, string propertyName, IDictionary&lt;string, object&gt; htmlAttributes)
          {
              html.ViewContext.Writer.Write(BeginControlGroupFor(html, propertyName, htmlAttributes));
              return new ControlGroup(html);
          }
      }
  
      public static class Alerts
      {
          public const string SUCCESS = &quot;success&quot;;
          public const string WARNING = &quot;warning&quot;;
          public const string ERROR = &quot;error&quot;;
          public const string INFORMATION = &quot;info&quot;;
  
          public static string[] ALL
          {
              get { return new[] { SUCCESS, WARNING, INFORMATION, ERROR }; }
          }
      }
  }
  </code></pre>
  <p><strong>ViewHelperExtensionClass</strong></p>
  <pre><code>namespace BootstrapSupport
  {
      public static class DefaultScaffoldingExtensions
      {
          public static string GetControllerName(this Type controllerType)
          {
              return controllerType.Name.Replace(&quot;Controller&quot;, String.Empty);
          }
  
          public static string GetActionName(this LambdaExpression actionExpression)
          {
              return ((MethodCallExpression)actionExpression.Body).Method.Name;
          }
  
          public static PropertyInfo[] VisibleProperties(this IEnumerable Model)
          {
              var elementType = Model.GetType().GetElementType();
              if (elementType == null)
              {
                  elementType = Model.GetType().GetGenericArguments()[0];
              }
              return elementType.GetProperties().Where(info =&gt; info.Name != elementType.IdentifierPropertyName()).ToArray();
          }
  
          public static PropertyInfo[] VisibleProperties(this Object model)
          {
              return model.GetType().GetProperties().Where(info =&gt; info.Name != model.IdentifierPropertyName()).ToArray();
          }
  
          public static RouteValueDictionary GetIdValue(this object model)
          {
              var v = new RouteValueDictionary();
              v.Add(model.IdentifierPropertyName(), model.GetId());
              return v;
          }
  
          public static object GetId(this object model)
          {
              return model.GetType().GetProperty(model.IdentifierPropertyName()).GetValue(model, new object[0]);
          }
  
  
          public static string IdentifierPropertyName(this Object model)
          {
              return IdentifierPropertyName(model.GetType());
          }
  
          public static string IdentifierPropertyName(this Type type)
          {
              if (type.GetProperties().Any(info =&gt; info.PropertyType.AttributeExists&lt;System.ComponentModel.DataAnnotations.KeyAttribute&gt;()))
              {
                  return
                      type.GetProperties().First(
                          info =&gt; info.PropertyType.AttributeExists&lt;System.ComponentModel.DataAnnotations.KeyAttribute&gt;())
                          .Name;
              }
              else if (type.GetProperties().Any(p =&gt; p.Name.Equals(&quot;id&quot;, StringComparison.CurrentCultureIgnoreCase)))
              {
                  return
                      type.GetProperties().First(
                          p =&gt; p.Name.Equals(&quot;id&quot;, StringComparison.CurrentCultureIgnoreCase)).Name;
              }
              return &quot;&quot;;
          }
  
          public static string GetLabel(this PropertyInfo propertyInfo)
          {
              var meta = ModelMetadataProviders.Current.GetMetadataForProperty(null, propertyInfo.DeclaringType, propertyInfo.Name);
              return meta.GetDisplayName();
          }
  
          public static string ToSeparatedWords(this string value)
          {
              return Regex.Replace(value, &quot;([A-Z][a-z])&quot;, &quot; $1&quot;).Trim();
          }
  
      }
  
      public static class PropertyInfoExtensions
      {
          public static bool AttributeExists&lt;T&gt;(this PropertyInfo propertyInfo) where T : class
          {
              var attribute = propertyInfo.GetCustomAttributes(typeof(T), false)
                                  .FirstOrDefault() as T;
              if (attribute == null)
              {
                  return false;
              }
              return true;
          }
  
          public static bool AttributeExists&lt;T&gt;(this Type type) where T : class
          {
              var attribute = type.GetCustomAttributes(typeof(T), false).FirstOrDefault() as T;
              if (attribute == null)
              {
                  return false;
              }
              return true;
          }
  
          public static T GetAttribute&lt;T&gt;(this Type type) where T : class
          {
              return type.GetCustomAttributes(typeof(T), false).FirstOrDefault() as T;
          }
  
          public static T GetAttribute&lt;T&gt;(this PropertyInfo propertyInfo) where T : class
          {
              return propertyInfo.GetCustomAttributes(typeof(T), false).FirstOrDefault() as T;
          }
  
          public static string LabelFromType(Type @type)
          {
              var att = GetAttribute&lt;DisplayNameAttribute&gt;(@type);
              return att != null ? att.DisplayName
                  : @type.Name.ToSeparatedWords();
          }
  
          public static string GetLabel(this Object Model)
          {
              return LabelFromType(Model.GetType());
          }
  
          public static string GetLabel(this IEnumerable Model)
          {
              var elementType = Model.GetType().GetElementType();
              if (elementType == null)
              {
                  elementType = Model.GetType().GetGenericArguments()[0];
              }
              return LabelFromType(elementType);
          }
      }
  
      //public static class HtmlHelperExtensions
      //{
      //    public static MvcHtmlString TryPartial(this HtmlHelper helper, string viewName, object model)
      //    {
      //        try
      //        {
      //            return helper.Partial(viewName, model);
      //        }
      //        catch (Exception)
      //        {
      //        }
      //        return MvcHtmlString.Empty;
      //    }
      //}
  }
  </code></pre>
  <p>and the <strong>_alert</strong> partial View</p>
  <pre><code>@using BootstrapSupport
  @if (TempData.ContainsKey(Alerts.WARNING))
  {
      &lt;div class=&quot;alert alert-block&quot;&gt;
          &lt;a class=&quot;close&quot; data-dismiss=&quot;alert&quot; href=&quot;#&quot;&gt;x&lt;/a&gt;
          &lt;h4 class=&quot;toast-title&quot;&gt;Attention!&lt;/h4&gt;
          @TempData[Alerts.WARNING]
      &lt;/div&gt;
  }
  @foreach (string key in Alerts.ALL.Except(new[] { Alerts.WARNING }))
  {
      if (TempData.ContainsKey(key))
      {
             
          &lt;div class=&quot;toast toast-top-full-width toast-key&quot;&gt;
              &lt;button type=&quot;button&quot; class=&quot;toast-close-button&quot; data-dismiss=&quot;alert&quot;&gt;x&lt;/button&gt;
              @TempData[key]
          &lt;/div&gt;
         
      }
  }
  </code></pre>
  <p>After all this I can send alert messages right from controller:</p>
  <p>And it works!</p>
  <p>For example</p>
  <pre><code>public ActionResult Test()
  {
     Success(&quot;Person was successfully added to your addressbook&quot;);
  }
  </code></pre>
  <p>above code would result this in view
  <img src="https://i.stack.imgur.com/f9HLM.jpg" alt="enter image description here" /></p>
  <p>but it is just displaying as content block. Not as I expected to work, as it just appears in view, no effect, nothing. I wanted it to work as in this site <a href="http://codeseven.github.io/toastr/demo.html" rel="nofollow noreferrer">Toastr</a>.</p>
  <p><em>I'm guessing I have to implement javascript somewhere in my <code>_alert</code> view and get the message and type(success, error,...) and then use javascript to growl it, to make it behave it as it should.
  But i don't have much knowledge about it.</em></p>
  <p>Something like below? Thats just idea, because of my lack of knowledge of Javascript and jquery i couldn't make it work</p>
  <pre><code> @*if (TempData.ContainsKey(key))
      {
          &lt;div class=&quot;toastMessageHolder&quot; style=&quot;display: none&quot;&gt;
              &lt;div class=&quot;toastMessage&quot;&gt;@TempData[key]&lt;/div&gt;
              &lt;div class=&quot;toastMessageType&quot;&gt;@key&lt;/div&gt;
          &lt;/div&gt;
     
      
                  
      if($(&quot;.toastMessageHolder&quot;))
          {
          //loop all toastMessageHolders
          $(&quot;.toastMessageHolder&quot;).foreach(function(){
              var message = $(&quot;.toastMessage&quot;, this).html();
              var messageType = $(&quot;.toastMessageType&quot;, this).html();
          });
          
              //feed this parameters to javascript 
          }*@
  </code></pre>
  <p>Could somebody help me how to make my growling from controller behave as mentioned in example of <a href="http://codeseven.github.io/toastr/demo.html" rel="nofollow noreferrer">Toastr</a>?</p>
  <p>If I had to growl from any normal view if I hadn't implemented sending msgs from controller to view this is how I would do using toastr:</p>
  <pre><code>function foo(response) {
          if (response.SomeTest) {
              toastr.error(response.ErrorMessage, &quot;Error&quot;);
          }
          else {
              $(@Html.IdFor(m=&gt;m.abc)).val('');
             
          }
          
      };
  </code></pre>
  <p><strong>Asp.Net MVC version: 5.1.1</strong></p>
  <p><strong>Growling package used: Toastr</strong></p>