How can I use NLog to get detail information regarding a local error?
Until now I have this:
private static Logger logger = LogManager.GetCurrentClassLogger();
public ActionResult Index()
{
try
{
var domain = db.Works.ToList();
var model = Mapper.Map<IList<Work>, IList<WorkIndexViewModels>>(domain);
return View(model);
}
catch (Exception e)
{
logger.Error("Error in Index: " + e);
}
}
If I put the return after the catch, the model is out of scope.
If I put the return inside the try, I get "not all code path returns a value" from the Action.
So how can I solve this?
Since you've already captured the error and you can't show the requested page, you could redirect within the catch to your error page:
catch (Exception e)
{
logger.Error("Error in Index: " + e);
return RedirectToAction("Index", "Error"); // Redirect to error controller or page
}
Alternatively, and probably more appropriate, you could have your action raise a 500 error so that your error configuration within your web.config can properly handle redirection.
catch (Exception e)
{
logger.Error("Error in Index: " + e);
return new HttpStatusCodeResult(500); // Raise internal server error
}
Related
I am unable to catch errors from when calling the Graph API.
Can anyone explain why I cannot catch the error? Simple example:
#using Microsoft.AspNetCore.Authorization
#using Microsoft.Graph
#attribute [Authorize]
#inject GraphServiceClient GraphClient
#if (allUsers != null)
{
foreach (var user in allUsers)
{
<tr>
<td>#user.DisplayName</td>
<td>#user.Mail</td>
<td>#user.UserPrincipalName</td>
</tr>
}
}
<h2>#errorMessage</h2>
#code {
private string errorMessage = "No errors";
private IEnumerable<Microsoft.Graph.User>? allUsers;
protected override async Task OnInitializedAsync()
{
var queryOptions = new List<QueryOption>
{
new QueryOption("$filter", "userType eq 'member1'") // causes a 400 error since member1 is not valid
};
try
{
//await Task.Delay(10000); // wait 10 seconds
allUsers = await GraphClient.Users.Request(queryOptions).GetAsync();
}
catch (ServiceException ex) // using catch (Exception ex) also doesn't work
{
Console.WriteLine("Error getting users from Graph: " + ex.Message);
Console.WriteLine("Error code: " + ex.Error.Code);
Console.WriteLine("Error inner message: " + ex.Error.InnerError.Message);
// Show error message to the user or log the error
errorMessage = "An error occurred while trying to get users from the Microsoft Graph API.";
}
Console.WriteLine(errorMessage);
}
}
When debugging it just skips over the catch block so it is not being triggered, and no errors are written the console. I know what the error is (using an invalid queryOption), I can see the error details in browser dev tools.
I am trying to login to our Application. When I input the username and the password and click login. It throws an error in the API. Saying: Incorrect Syntax near the keywoard 'IF'.
Here is the image for full exception details.
Full Exception Details
I tried to debug the solution and it starts from here:
[HttpGet]
[ActionName("checkUser")]
public HttpResponseMessage IsUserActive(string userNames)
{
try
{
var isActive = _userService.IsUserActive(userNames);
return Helper.ComposeResponse(HttpStatusCode.OK, isActive);
}
catch (Exception e)
{
throw e;
}
}
After this, it will then be redirected to this method/function:
public bool IsUserActive(string username)
{
try
{
var result = RetrieveAll().Where(x => x.Username.Equals(username));
return result.Any();
}
catch (Exception e)
{
throw e;
}
}
After this function, it will then be redirected to below function.
Then it will throw the exception in this line of code specifically in
return GetDbSet<User>().Where(x => x.DeleteFlag == false).OrderByPropertyName("LastName", SortDirection.Ascending);
public IQueryable<User> RetrieveAll()
{
try
{
return GetDbSet<User>().Where(x => x.DeleteFlag == false).OrderByPropertyName("LastName", SortDirection.Ascending);
}
catch (Exception e)
{
throw e;
}
}
GetDbSet Contains this line of code.
protected virtual DbSet<TEntity> GetDbSet<TEntity>() where TEntity : class
{
return Context.Set<TEntity>();
}
OrderByPropertyName Contains this line of code.
public static IQueryable<T> OrderByPropertyName<T>(this IQueryable<T> query, string attribute, SortDirection direction)
{
return ApplyOrdering(query, attribute, direction, "OrderBy");
}
I don't know what's wrong or where is that "IF" coming from or where should I edit for me to go proceed in logging in the application. I really appreciate your help. Thanks in advance.
I have tried in Global.asax.cs
protected void Application_BeginRequest(object sender, EventArgs e)
{
try
{
var cookiesDataUserinfo = HttpContext.Current.Request.Cookies["UserInfo"];
if (cookiesDataUserinfo != null)
{
Session["UserId"] = cookiesDataUserinfo["UserId"].ToString();
}
}
catch (Exception ex)
{
string msg = ex.Message;
}
}
But I am getting the error "Session state is not available in this context."
I also tried to load data from cookies in constructor of a controller. But cookies is null inside constructor.
Is there any way where I can set session values from cookies before any view is rendered in my MVC project?
I have found the solution I was looking for. I need to use the Application_AcquireRequestState method in Global.asax.cs
protected void Application_AcquireRequestState(object sender, EventArgs e)
{
try
{
var cookiesDataUserinfo = HttpContext.Current.Request.Cookies["UserInfo"];
if (cookiesDataUserinfo != null)
{
Session["UserId"] = cookiesDataUserinfo["UserId"].ToString();
}
}
catch (Exception ex)
{
string msg = ex.Message;
}
}
For every request the Application_AcquireRequestState method is called and I can set session values from Cookies if available.
I want to call service with the same routing name(same parameter ) with different versions ...
bellow is the my code
[Route("api/v{version:apiVersion}/[controller]/")]
[ApiController]
[ApiVersion("1.0")]
[ApiVersion("1.1")]
public class AccountController : ControllerBase
{
[MapToApiVersion("1")]
[HttpGet("getacounttypes")]
[ProducesResponseType(typeof(Models.ReturnString), StatusCodes.Status200OK)]
[ProducesResponseType(typeof(Models.ErrorMessage), StatusCodes.Status400BadRequest)]
[ProducesResponseType(typeof(Models.ErrorMessage), StatusCodes.Status500InternalServerError)]
public async Task<ActionResult> GetAddressTypes()
{
logger.LogInformation("Request is processing at account types");
try
{
return Ok(await accountBS.GetAccountTypes());
}
catch (ArgumentException ex)
{
logger.LogError(ex, ex.Message);
this.Response.StatusCode = StatusCodes.Status400BadRequest;
return new JsonResult(new Models.ErrorMessage() { Code = StatusCodes.Status400BadRequest.ToString(), Message = ex.Message });
}
catch (Exception e)
{
logger.LogError(e, e.Message);
this.Response.StatusCode = StatusCodes.Status500InternalServerError;
return new JsonResult(new Models.ErrorMessage() { Code = StatusCodes.Status500InternalServerError.ToString(), Message = e.Message });
}
}
[MapToApiVersion("1.1")]
[HttpGet("getacounttypes")]
[ProducesResponseType(typeof(Models.ReturnString), StatusCodes.Status200OK)]
[ProducesResponseType(typeof(Models.ErrorMessage), StatusCodes.Status400BadRequest)]
[ProducesResponseType(typeof(Models.ErrorMessage), StatusCodes.Status500InternalServerError)]
public async Task<ActionResult> GetAddressTypesV1_1()
{
logger.LogInformation("Request is processing at account types");
try
{
return Ok(await accountBS.GetAccountTypes());
}
catch (ArgumentException ex)
{
logger.LogError(ex, ex.Message);
this.Response.StatusCode = StatusCodes.Status400BadRequest;
return new JsonResult(new Models.ErrorMessage() { Code = StatusCodes.Status400BadRequest.ToString(), Message = ex.Message });
}
catch (Exception e)
{
logger.LogError(e, e.Message);
this.Response.StatusCode = StatusCodes.Status500InternalServerError;
return new JsonResult(new Models.ErrorMessage() { Code = StatusCodes.Status500InternalServerError.ToString(), Message = e.Message });
}
}
}
in this im having error like
An unhandled exception has occurred while executing the request.
System.NotSupportedException: HTTP method "GET" & path "api/v{version}/Account/[actions]/getacounttypes" overloaded by actions - API.Controllers.AccountController.GetAddressTypes (GSOnline.API),
API.Controllers.AccountController.GetAddressTypesV1_1 . Actions require unique method/path combination for Swagger 2.0. Use ConflictingActionsResolver as a workaround
at Swashbuckle.AspNetCore.SwaggerGen.SwaggerGenerator.CreatePathItem(IEnumerable`1 apiDescriptions, ISchemaRegistry schemaRegistry)
at System.Linq.Enumerable.ToDictionary[TSource,TKey,TElement](IEnumerable`1 source, Func`2 keySelector, Func`2 elementSelector, IEqualityComparer`1 comparer)
at Swashbuckle.AspNetCore.SwaggerGen.SwaggerGenerator.CreatePathItems(IEnumerable`1 apiDescriptions, ISchemaRegistry schemaRegistry)
at Swashbuckle.AspNetCore.SwaggerGen.SwaggerGenerator.GetSwagger(String documentName, String host, String basePath, String[] schemes)
at Swashbuckle.AspNetCore.Swagger.SwaggerMiddleware.Invoke(HttpContext httpContext, ISwaggerProvider swaggerProvider)
at Microsoft.AspNetCore.Builder.RouterMiddleware.Invoke(HttpContext httpContext)
at Microsoft.AspNetCore.Builder.RouterMiddleware.Invoke(HttpContext httpContext)
at Microsoft.AspNetCore.StaticFiles.StaticFileMiddleware.Invoke(HttpContext context)
at Microsoft.AspNetCore.Diagnostics.StatusCodePagesMiddleware.Invoke(HttpContext context)
at Microsoft.AspNetCore.Diagnostics.EntityFrameworkCore.MigrationsEndPointMiddleware.Invoke(HttpContext context)
at Microsoft.AspNetCore.Diagnostics.EntityFrameworkCore.DatabaseErrorPageMiddleware.Invoke(HttpContext httpContext)
at Microsoft.AspNetCore.Diagnostics.EntityFrameworkCore.DatabaseErrorPageMiddleware.Invoke(HttpContext httpContext)
at Microsoft.AspNetCore.Diagnostics.DeveloperExceptionPageMiddleware.Invoke(HttpContext context)
so could u please suggest me the solution for the same routing with same parameters with diff versions ??
i can manage method with diff parameters but im looking same routing with same parametrs ...
expecting result is
GET
/api/v1/Account/getacounttypes
GET
/api/v1.1/Account/getacounttypes
Your question is not entirely clear, but it appears you are referring to generating a single OpenAPI/Swagger document with Swashbuckle. Normally, Swashbuckle will create a single document per API version. Using the URL segment method, it is possible to create a single document with all of the URLs. The document only allows distinct URLs, which are derived from route templates. The route parameter is filled in at request time, but the document generator doesn't know or otherwise understand that.
To achieve this behavior, you need to have the API Explorer fill in the API version when it generates descriptions. Your configuration should look like this:
services.AddVersionedApiExplorer(options => options.SubstituteApiVersionInUrl = true);
With this option configured, the API version will be substituted automatically on your behalf and achieve your expected results.
i have read the post that have same problem as mine
JSF ViewScope - returning null on actions do not update the view
but it haven't worked for me cause i already use the h:commandLink in another page and its works perfectly but in this page it doesn't .
this is the request Bean
public class AddSectionBean {
public String delete(String id) {
try {
HttpSession session = SessionUtil.getSession();
UserVO userVOCreater = (UserVO) session.getAttribute("userVO");
SectionsDao.getInstance().deleteSectionById(
Integer.parseInt(id));
LoggerVO loggerVO =new LoggerVO();
loggerVO.setUserid(userVOCreater.getId());
loggerVO.setLog("deleted Section Id:"+id);
LoggerDao.getInstance().insertLogger(loggerVO);
} catch (Exception e) {
e.printStackTrace();
BundleMessages.getInstance().setMessage("error",
FacesMessage.SEVERITY_ERROR);
logger.error(e.getMessage(), e);
}
return null;
}
}
and the link is inside a richtable for every column
<rich:column>
<h:commandLink id="actualDelete" styleClass="delete_#{sectionsBean.datatableSections.rowIndex}" action ="#{addSectionBean.delete(s.id)}" />
</rich:column>
Note That: i tried to return the outcome instead of null but when i do that i lose the style and scripts in page
, note that the scripts have no effect cause i have tested it with them and had the same result
the problem solved by moving the delete method to the bean that view the table and calling the database method again inside the delete function to reload the table even its reloads in the postConstruct function
public class SectionsBean{
List<SectionVO> sectionsList = new ArrayList<SectionVO>();
#PostConstruct
public void postConstruct() {
try {
this.sectionsList = SectionsDao.getInstance().getSections();
} catch (Exception e) {
e.printStackTrace();
logger.error(e.getMessage(), e);
}
}
public String delete(String id) {
try {
HttpSession session = SessionUtil.getSession();
UserVO userVOCreater = (UserVO) session.getAttribute("userVO");
SectionsDao.getInstance().deleteSectionById(
Integer.parseInt(id));
LoggerVO loggerVO =new LoggerVO();
loggerVO.setUserid(userVOCreater.getId());
loggerVO.setLog("deleted Section Id:"+id);
LoggerDao.getInstance().insertLogger(loggerVO);
//reload the database table
this.sectionsList = SectionsDao.getInstance().getSections();
} catch (Exception e) {
e.printStackTrace();
BundleMessages.getInstance().setMessage("error",
FacesMessage.SEVERITY_ERROR);
logger.error(e.getMessage(), e);
}
BundleMessages.getInstance().setMessage("success",
FacesMessage.SEVERITY_INFO);
System.out.println("calling delete id="+id);
return null;
}
}