
Hangfire dashboard access with JWT token authentication
While attempting to access the Hangfire dashboard of a ASP.NET Web API project recently, we realised we had been denied access.
Earlier this year we changed our development stack and began using Angular and ASP.NET Web API. Before this change, we were using ASP.NET MVC systems utilizing Razor views. We also use Hangfire for background processing, which allows us to offload certain processing to background threads. Once we had deployed our first project we realized that some of our Hangfire tasks weren’t completing and in attempting to debug the issue we tried to view the Hangfire dashboard. When we were greeted with a white page we realized that we did not have access to the dashboard. Our custom HangfireAuthorizationFilter was denying us access because it was still validating users against the HttpContext object.
Our API was using JWT bearer tokens for authorization, so we needed to take another look at our HangfireAuthorizationFilter logic.
public bool Authorize([NotNull] DashboardContext context) { #if DEBUG // If we are in debug, always allow Hangfire access. return true; #else // if we have a cookies and we are in release mode HttpCookieCollection cookies = System.Web.HttpContext.Current.Request.Cookies; if (cookies["custom_cookie_name"] != null) { HttpCookie jwtCookie = cookies["custom_cookie_name"]; string jwtToken = jwtCookie.Value; JwtSecurityTokenHandler handler = new JwtSecurityTokenHandler(); JwtSecurityToken securityToken = handler.ReadToken(jwtToken) as JwtSecurityToken; // return true or false based on the presence of a specific claim e.g role claim // string role = securityToken.Claims.First(claim => claim.Type == "role").Value; // return role == "THE_ROLE_WE_ARE_LOOKING_FOR"; } return false; #endif }
In order to make this process work, we use Postman to create an API request to our token URL (e.g. [cci]http://systemurl/token[/cci]) and use the return bearer token as the value that our cookie contains.
Thank you for sharing – very helpful as we were running into a similar scenario!
Glad we could help, this was a really annoying problem to run into.