Application_Error does not handle exception - asp.net-mvc

I am working on MVC Application.
I have FilterConfig class :
public class FilterConfig
{
public static void RegisterGlobalFilters(GlobalFilterCollection filters)
{
filters.Add(new HandleErrorAttribute());
}
}
I am using it in Global.asax.cs
protected void Application_Start()
{
AreaRegistration.RegisterAllAreas();
FilterConfig.RegisterGlobalFilters(GlobalFilters.Filters);
RouteConfig.RegisterRoutes(RouteTable.Routes);
BundleConfig.RegisterBundles(BundleTable.Bundles);
}
If i use this approach my Application_Error does not get fired when any exception occurs in controller.
protected void Application_Error()
{
var exception = Server.GetLastError();
AppLogging.WriteError(exception);
var httpException = exception as HttpException;
Response.Clear();
Server.ClearError();
var routeData = new RouteData();
routeData.Values["controller"] = "Error";
routeData.Values["action"] = "Error";
routeData.Values["exception"] = exception;
Response.StatusCode = 500;
if (httpException != null)
{
Response.StatusCode = httpException.GetHttpCode();
switch (Response.StatusCode)
{
case 403:
routeData.Values["action"] = "UnauthorizedAccess";
break;
case 503:
routeData.Values["action"] = "SiteUnderMaintenance";
break;
case 404:
routeData.Values["action"] = "PageNotFound";
break;
}
}
// Avoid IIS7 getting in the middle
Response.TrySkipIisCustomErrors = true;
IController errorsController = new ErrorController();
HttpContextWrapper wrapper = new HttpContextWrapper(Context);
var rc = new RequestContext(wrapper, routeData);
errorsController.Execute(rc);
}
public ActionResult Error()
{
return View("Error");
}
Now when i do customErrors mode="Off" it goes to Application_Error Event but HandleErrorInfo comes as null.
Error.cshtml
#model HandleErrorInfo
#{
Layout = "~/Views/Shared/_LayoutAnonymous.cshtml";
ViewBag.Title = "Error";
}
<div class="error_wrapper">
<div class="col-sm-12 col-xs-12">
<div class=" error_col">
<div style="display: none;">
#if (Model != null)
{
<h3>#Model.Exception.GetType().Name</h3>
<pre>
#Model.Exception.ToString()
</pre>
<p>
thrown in #Model.ControllerName #Model.ActionName
</p>
}
</div>
<h1 class="error_h1">503 </h1>
<h2 class="error_h2">Looks like we're having some server issues. </h2>
<h3 class="error_h3">
Go back to the previous page and try again.<br>
If you think something is broken, report a problem.
</h3>
<div class="col-sm-12 col-xs-12 padding_none">
<button class="btn btn-primary btn_box error_btn" id="btnReport">Report A Problem</button>
<button class="btn btn-primary btn_box error_btn pull-left" onclick="location.href='#Url.Action("Requests", "Pricing", new RouteValueDictionary { { "area", "" } })'"> Go To Homepage</button>
</div>
</div>
</div>
</div>
#Scripts.Render("~/bundles/Error")

This is because your web config settings <customErrors mode="On" /> are overriding the default behavior. You will need to disable this setting. if you disable this, you can handle the error in the Application_Error event then redirect the user or display a message from this event. This web config setting is handling the errors and only unhandled errors will bubble up to the Application_Error event.

Related

Checkbox Form Submit trigger Logout in Identity EntityFramework on _loginpartial-C# asp.net MVC

I have a checkbox(justdoit) on asp.net MVC create view. If checkbox checked, it submits#onclick = "document.forms[0].submit() value and according to that, if else condition disable or enable other dropbox form("Status) in view.It was working without problem. After I integrated authorization to page(Microsoft.AspNetCore.Identity.EntityFrameworkCore" Version="6.0.10), I added _loginpartial to _layout.cshtml page. Then I log in page with authorised user and enter create item page,when I check to checkbox(onlick submit works), log out is trigered and I log out the site and find myself on the indexpage. After that I tried to create item without login, it works without problem. Therefore I think checkbox submit trigger the logout.(Project.Identity.Pages.Account.LogoutModel: Information: User logged out.) How Can I solve that problem?
Thank you for answer in advance
Code in the view:
#Html.CheckBox("Justdoit", false, new { #onclick = "document.forms[0].submit();" })
Justdoit
<br />
#if(Convert.ToBoolean(ViewBag.Justdoit))
{
<div class="form-group">
<label asp-for="Status" class="control-label">Status (Choose One)</label>
<select asp-for="Status" class="form-control" id="Status" disabled>
<option>Completed</option>
</select>
<span asp-validation-for="Status" class="text-danger"></span>
</div>
}
else
{
<div class="form-group">
<label asp-for="Status" class="control-label">Status (Choose One)</label>
<select asp-for="Status" class="form-control" id="Status" >
<option>Completed</option>
<option>Plan</option>
<option>Do</option>
<option>Study</option>
<option>Act</option>
</select>
<span asp-validation-for="Status" class="text-danger"></span>
</div>
}
</td>
Code in the _loginpartial
<li class="nav-item">
<form id="logoutForm" class="form-inline" asp-area="Identity" asp-page="/Account/Logout" asp-route-returnUrl="#Url.Action("Index", "Home", new { area = "" })">
<button id="logout" type="submit" class="nav-link btn btn-link text-dark">Logout</button>
</form>
</li>
Item controller- It logs out before calling ViewBag.
[HttpPost]
[ValidateAntiForgeryToken]
public async Task<IActionResult>Create(bool Justdoit,[Bind("Id,Title,Description,MainBody,Team,Owner,StartDate,Status,Justdoit,Category")] Suggestion suggestion)
{
ViewBag.Justdoit = Justdoit;
if (ModelState.IsValid)
{
_context.Add(suggestion);
await _context.SaveChangesAsync();
return RedirectToAction(nameof(Index));
}
return View(suggestion);
}
Logout model View
#page
#model LogoutModel
#{
ViewData["Title"] = "Log out";
}
<header>
<h1>#ViewData["Title"]</h1>
#{
if (User.Identity.IsAuthenticated)
{
<form class="form-inline" asp-area="Identity" asp-page="/Account/Logout" asp-route-returnUrl="#Url.Page("/", new { area = "" })" method="post">
<button type="submit" class="nav-link btn btn-link text-dark">Click here to Logout</button>
</form>
}
else
{
<p>You have successfully logged out of the application.</p>
}
}
</header>
Logout model cshtml.cs file
public class LogoutModel : PageModel
{
private readonly SignInManager<ApplicationUser> _signInManager;
private readonly ILogger<LogoutModel> _logger;
public LogoutModel(SignInManager<ApplicationUser> signInManager, ILogger<LogoutModel> logger)
{
_signInManager = signInManager;
_logger = logger;
}
public async Task<IActionResult> OnPost(string returnUrl = null)
{
await _signInManager.SignOutAsync();
_logger.LogInformation("User logged out.");
if (returnUrl != null)
{
return LocalRedirect(returnUrl);
}
else
{
// This needs to be a redirect so that the browser performs a new
// request and the identity for the user gets updated.
return RedirectToPage();
}
}
}
Enable or Disable form based on Condition in ASP.Net MVC. Condition is created by clicking the checkbox. I want to use that feature on the authorized page.

httpPost return Page not found HTTP ERROR 405 ASP.NET CORE MVC IIS Express

i have problem with form when i put in my Controller httpPost the Error http 405 it showing to me
every step i made its correct
my code
#model security.Models.ContactUs
<div class="contact_box">
<form id="Contact" asp-controller="Home" asp-action="Contact" method="POST">
<input type="text" asp-for="Name" placeholder="Your Name">
<input type="email" asp-for="Email" placeholder="Email">
<input type="text" asp-for="PhoneNumber" placeholder="Phone Number">
<input type="text" asp-for="Text" placeholder="Message">
<button type="submit">Contact Us</button>
</form>
</div>
and my Controller
namespace security.Controllers
{
public class HomeController : Controller
{
DBContext db;
public HomeController(DBContext context)
{
db = context;
}
//private readonly ILogger<HomeController> _logger;
//public HomeController(ILogger<HomeController> logger)
//{
// _logger = logger;
//}
[HttpGet]
public IActionResult Index()
{
CollectionsData model = new CollectionsData();
model.Offers = GetOffers();
model.Services = GetServices();
model.News = GetNews();
model.Team = GetSecurityTeam();
return View(model);
}
[HttpPost]
public IActionResult Contact(ContactUs model)
{
db.Contactus.Add(model);
db.SaveChanges();
return RedirectToAction("Index");
}
public IActionResult Services( Sevices model)
{
var ModelServices = db.Sevices.ToList();
return View(ModelServices);
}
//[ResponseCache(Duration = 0, Location = ResponseCacheLocation.None, NoStore = true)]
//public IActionResult Error()
//{
// return View(new ErrorViewModel { RequestId = Activity.Current?.Id ?? HttpContext.TraceIdentifier });
//}
public IEnumerable<Offers> GetOffers()
{
return db.Offers.ToList();
}
public IEnumerable<Sevices> GetServices()
{
return db.Sevices.ToList();
}
public IEnumerable<ourNews> GetNews()
{
return db.News.ToList();
}
public IEnumerable<SecurityTeam> GetSecurityTeam()
{
return db.Team.ToList();
}
}
}
But when I delete httppost everything works fine except sending the form to the database
i don't why the page its not load its give HTTP ERROR 405
thanks
you have to place a submit button inside of the form
<form asp-controller="Home" asp-action="Contact" method="POST">
....your code
<button type="submit">Contact Us</button>
</form>
or for some reason sometimes this works better
#using (Html.BeginForm("Contact", "Home", FormMethod.Post))
{
....your code
<button type="submit">Contact Us</button>
}
and you need Contact get action to create a contact view
[HttpGet]
public IActionResult Contact()
{
var model= new ContactUs();
return View(model)
}
try this
<form id="contact" method="POST" asp-action="Contact">
...
</form>
return View() doesn’t make any sense from an HTTP Verb perspective. Your form is POSTing correctly, but when you’re returning the view you need to change it to redirect to your GET action. I don’t know know what your entire controller looks like but I suspect this is the issue with naming.
Try
return RedirectToAction(“VIEWNAME”)

Unable to cast object of type 'Microsoft.Asp.NetCore.Http.FormFile' to type 'System.IO.Stream' in Asp.NetCore MVC web app

I am a newbie to Asp.netCore as well as Microsoft Azure. Recently, I am trying to integrate ASP.net Core MVC web app with blob storage.
In the application I upload an file (image) to the azure blob storage, and the URL of the uploaded file is stored in the Microsoft SQL database. The database is connected to the application perfectly and it is working fine too.
I have created an Azure blob storage and I have already created containers and have manually uploaded files to the blob storage. Blob storage also working perfect.
This is the controller class: (I have put the image uploading controllers in the 'HomeController' for the testing purposes
using Microsoft.AspNetCore.Authorization;
using Microsoft.AspNetCore.Http;
using Microsoft.AspNetCore.Identity;
using Microsoft.AspNetCore.Mvc;
using Microsoft.Extensions.Logging;
using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.IO;
using System.Linq;
using System.Threading.Tasks;
using WebAppMVC.Data;
using WebAppMVC.Models;
using WebAppMVC.Utilities;
namespace WebAppMVC.Controllers
{
public class HomeController : Controller
{
private readonly UserManager<WebAppMVCUser> _userManager;
private readonly ILogger<HomeController> _logger;
public HomeController(ILogger<HomeController> logger,UserManager<WebAppMVCUser> userManager)
{
_logger = logger;
/* newly added */
_userManager = userManager;
utility = new BlobUtility(accountName, accountKey);
db = new WebAppMVC_DBContext();
/* newly added */
}
/* newly added */
BlobUtility utility;
WebAppMVC_DBContext db;
string accountName = "_my_Storage_Name";
string accountKey = "My_storage_account_key";
/* newly added */
[Authorize]
public IActionResult Index()
{
/* newly added */
string loggedInUserId = _userManager.GetUserId(User);
List<UserMedium> userMedia = (from a in db.UserMedia where a.UserId.ToString() == loggedInUserId select a).ToList();
ViewBag.PhotoCount = userMedia.Count;
return View(userMedia);
/* newly added */
}
/* newly added */
[Authorize]
public ActionResult DeleteImage(int id)
{
UserMedium userImage = db.UserMedia.Find(id);
db.UserMedia.Remove(userImage);
db.SaveChanges();
string BlobNameToDelete = userImage.ImageUrl.Split('/').Last();
utility.DeleteBlob(BlobNameToDelete, "profilepics");
return RedirectToAction("Index");
}
[Authorize]
[HttpPost]
public ActionResult UploadImage(IFormFile file)
{
if (file != null)
{
string ContainerName = "profilepics"; // container name.
//file = Request.File["file"];
string fileName = Path.GetFileName(file.FileName);
Stream imageStream = file.OpenReadStream();
var result = utility.UploadBlob(fileName, ContainerName, (Stream)file);
if (result != null)
{
string loggedInUserId = _userManager.GetUserId(User);
UserMedium usermedium = new UserMedium();
usermedium.MediaId = new Random().Next();
try
{
usermedium.UserId = Int32.Parse(loggedInUserId);
}
catch
{
Console.WriteLine($"Unable to parse '{loggedInUserId}'");
}
usermedium.ImageUrl = result.Uri.ToString();
db.UserMedia.Add(usermedium);
db.SaveChanges();
return RedirectToAction("Index");
}
else
{
return RedirectToAction("Index");
}
}
else
{
return RedirectToAction("Index");
}
}
/* newly added */
[Authorize]
public IActionResult Privacy()
{
return View();
}
[Authorize]
public IActionResult Media()
{
return View();
}
public IActionResult InformationPortal()
{
return View();
}
[ResponseCache(Duration = 0, Location = ResponseCacheLocation.None, NoStore = true)]
public IActionResult Error()
{
return View(new ErrorViewModel { RequestId = Activity.Current?.Id ?? HttpContext.TraceIdentifier });
}
}
}
This is the View Index.cshtml code: (I am uploading the file from the Index.cshtml) Uploading-Image-from-the-view
#model IEnumerable<WebAppMVC.Models.UserMedium>
<div class="container">
<div class="row">
#using (Html.BeginForm("UploadImage", "Home", FormMethod.Post, new { enctype = "multipart/form-data" }))
{
<div class="panel panel-warning">
<div class="panel-heading">
<h3 class="panel-title">Upload and save your photo</h3>
</div>
<div class="panel-body">
<div class="row">
<div class="col-md-4 col-md-offset-4">
<input type="file" name="file" />
<br />
<input type="submit" class="btn btn-warning form-control" value="Save Photo" />
</div>
</div>
</div>
</div>
}
</div>
<br />
<div class="row">
<div class="col-lg-12">
<div class="alert alert-warning">You have #ViewBag.PhotoCount Photos </div>
</div>
#foreach (var item in Model)
{
<div class="col-lg-3 col-md-4 col-xs-6 thumb">
<a class="thumbnail" href="#item.ImageUrl">
<img class="img-responsive" src="#item.ImageUrl" style="height: 300px;width:100%;" alt="">
</a>
<a href="#Url.Action("DeleteImage", "Home",new { id = item.MediaId })" class="btn btn-default btn-block">
<span class="glyphicon glyphicon-remove" aria-hidden="true"></span>
</a>
</div>
}
</div>
But when I run the app, after uploading the file(jpg image) I am getting the following exception:
This exception comes and application also put into the break mode.
Exception: Click-here-to-see-the-exception
As depicted in the picture, the application is put into the break mode and that exception is thrown at the line 74 of HomeController (The controller I used to control the file upload).
Following is the detailed description of the exception: exception-details
And when I step forward, I am getting this error message on the browser: Exception-error-on-browser
I do not understand the error and Does anybody know how to solve this issue?
Thanks in advance.
Try this function to convert IFormFile to Stream.
public static async Task<Stream> GetStream(this IFormFile formFile)
{
using (var memoryStream = new MemoryStream())
{
await formFile.CopyToAsync(memoryStream);
return memoryStream;
}
}
This will work for you:
IFormFile file;
byte[]? image = Array.Empty<byte>();
if (file != null)
{
await using var memoryStream = new MemoryStream();
await file!.CopyToAsync(memoryStream);
image = memoryStream.ToArray();
}

MVC redirect to error page doesn't display message

In MVC I am trying to redirect a message to an Error page when it occurs. The Error Page will open but I get no error message.
This is the method that initiates the process.
[HttpPost]
public ActionResult SaveSurvey(vmFollowUpSurvey model)
{
var result = surveyBL.postSurveyResults(model);
if (result != "Record Saved")
{
ModelState.AddModelError(string.Empty, "Survey not saved");
var redirectUrl = new UrlHelper(Request.RequestContext).Action("Index", "Error");
return Json(new { Url = redirectUrl });
}
else
{
ModelState.AddModelError(string.Empty, "Survey completed");
var redirectUrl = new UrlHelper(Request.RequestContext).Action("Index", "Login");
return Json(new { Url = redirectUrl });
}
}
My ErrorController then has a method of
public ActionResult Index()
{
return View();
}
And my View displays as this
<h2>Survey Information Page</h2>
<div>
#using (Html.BeginForm("Index", "Error"))
{
<div class="container">
<div class="row">
#Html.ValidationSummary(false, "", new { #class = "text-info" })
</div>
</div>
}
</div>
So what did I not do to get this to display?
Your ErrorController.Index() method has no knowledge of the model being used, so adding the message to ModelState will mean your error page doesn't have access to it. If you're going to be redirecting to a different view, the proper way to handle this would be to put the error inside the Session.
if (result != "Record Saved")
{
Session["Error"] = "Survey not saved";
...
}
Then inside your Error view, you can do something like this:
<h2>Survey Information Page</h2>
<div>
#using (Html.BeginForm("Index", "Error"))
{
<div class="container">
<div class="row">
<span class="error-message">#Session["Error"]</span>
</div>
</div>
}
</div>
[HttpPost]
public ActionResult SaveSurvey(vmFollowUpSurvey model)
{
var result = surveyBL.postSurveyResults(model);
if (result != "Record Saved")
{
return RedirectToAction("Index", "Error", new { ErrorMessage= "Survey not saved"} );
}
else
{
ModelState.AddModelError(string.Empty, "Survey completed");
var redirectUrl = new UrlHelper(Request.RequestContext).Action("Index", "Login");
return Json(new { Url = redirectUrl });
}
}
--- ErrorModel Class
namespace WebApplication3.Models
{
public class ErrorModel
{
public string ErrorMessage { get; set; }
}
}
--- Error Index.html code
#model WebApplication3.Models.ErrorModel
<h2>Survey Information Page</h2>
<div>
#using (Html.BeginForm("Index", "Error"))
{
<div class="container">
<div class="row">
#Html.ValidationSummary(false, Model.ErrorMessage , new { #class = "text-info" })
</div>
</div>
}
</div>

ASP.NET Entity Framework success message after registration

I am really trying hard to make a popup message (success or error) when the user has finished registration. So in the AccountController, I made a ViewBag but since it redirects to Login right away, I've noticed that the message is not appearing or popping up.
How do I show the message?
public async Task<ActionResult> Register(RegisterViewModel model)
{
if (ModelState.IsValid)
{
....
ViewBag.message= "Registered Successfully";
return RedirectToAction("Login", "Account");
}
}
_Layout view:
<div class="container body-content">
#if (ViewBag.message!= null)
{
if (ViewBag.message.Equals("Registered Successfully"))
{
<div class="alert alert-success fade in">
×
<strong>Success!</strong> #ViewBag.message
</div>
}
}
#RenderBody()
</div>
You may use TempData instead of the ViewBag
if (ModelState.IsValid)
{
TempData["Message"] = "Registered Successfully";
return RedirectToAction("Login", "Account");
}
In your view:
<div class="container body-content">
#if (TempData["Message"] != null)
{
...
}
#RenderBody()
</div>

Resources