How I would imitate User.IsInRole ()

I have a website that is built using the VS 2012 Internet application (simple membership) EF Code First

Updates

I would like to know how to extend the functionality of HttpContext.User.IsInRole(role) for a user table -> User.IsInClient(client) .

+6
source share
4 answers

Here's how I suggest solving your problem:

Create your own interface that implements System.Security.Principal , where you can place any methods that you need:

 public interface ICustomPrincipal : IPrincipal { bool IsInClient(string client); } 

Implement this interface:

 public class CustomPrincipal : ICustomPrincipal { private readonly IPrincipal _principal; public CustomPrincipal(IPrincipal principal) { _principal = principal; } public IIdentity Identity { get { return _principal.Identity; } } public bool IsInRole(string role) { return _principal.IsInRole(role); } public bool IsInClient(string client) { return _principal.Identity.IsAuthenticated && GetClientsForUser(_principal.Identity.Name).Contains(client); } private IEnumerable<string> GetClientsForUser(string username) { using (var db = new YourContext()) { var user = db.Users.SingleOrDefault(x => x.Name == username); return user != null ? user.Clients.Select(x => x.Name).ToArray() : new string[0]; } } } 

In Global.asax.cs, assign your user principle in the context of the request user (and, if necessary, to the executable stream if you plan to use it later). I suggest using the Application_PostAuthenticateRequest event not the Application_AuthenticateRequest for this purpose, otherwise your main one will be overridden (at least ASP.NET MVC 4):

 protected void Application_PostAuthenticateRequest(Object sender, EventArgs e) { Context.User = Thread.CurrentPrincipal = new CustomPrincipal(User); /* * BTW: Here you could deserialize information you've stored earlier in the * cookie of authenticated user. It would be helpful if you'd like to avoid * redundant database queries, for some user-constant information, like roles * or (in your case) user related clients. Just sample code: * * var authCookie = Request.Cookies[FormsAuthentication.FormsCookieName]; * var authTicket = FormsAuthentication.Decrypt(authCookie.Value); * var cookieData = serializer.Deserialize<CookieData>(authCookie.UserData); * * Next, pass some deserialized data to your principal: * * Context.User = new CustomPrincipal(User, cookieData.clients); * * Obviously such data have to be available in the cookie. It should be stored * there after you've successfully authenticated, eg in your logon action: * * if (Membership.ValidateUser(user, password)) * { * var cookieData = new CookieData{...}; * var userData = serializer.Serialize(cookieData); * * var authTicket = new FormsAuthenticationTicket( * 1, * email, * DateTime.Now, * DateTime.Now.AddMinutes(15), * false, * userData); * * var authTicket = FormsAuthentication.Encrypt(authTicket); * var authCookie = new HttpCookie(FormsAuthentication.FormsCookieName, authTicket); * Response.Cookies.Add(authCookie); * return RedirectToAction("Index", "Home"); * } */ } 

Then, in order to be able to use the User property from the HttpContext in the controller, without changing it to ICustomPrincipal each time, define the base controller where you will override the default User property:

 public class BaseController : Controller { protected virtual new ICustomPrincipal User { get { return (ICustomPrincipal)base.User; } } } 

Now let other controllers inherit from it:

 public class HomeController : BaseController { public ActionResult Index() { var x = User.IsInClient(name); 

If you use the Razor View Engine , and you would like to be able to use your method in a very similar way:

 @User.IsInClient(name) 

you need to override the type of WebViewPage :

 public abstract class BaseViewPage : WebViewPage { public virtual new ICustomPrincipal User { get { return (ICustomPrincipal)base.User; } } } public abstract class BaseViewPage<TModel> : WebViewPage<TModel> { public virtual new ICustomPrincipal User { get { return (ICustomPrincipal)base.User; } } } 

and tell Razor to reflect your changes by changing the appropriate section of the Views \ Web.config file:

 <system.web.webPages.razor> ... <pages pageBaseType="YourNamespace.BaseViewPage"> 
+14
source

Use Linq:

 var Users = Membership.GetAllUsers(); //**Kinda Like Users.InCLients(userName). var users = from x in Users join y in db.Clinets on x.ProviderUserKey equals y.UserID select x //**Kinda Like Clients.InUsers(userName) var clients = from x in db.Clinets join y in Users on x.UserID equals y.ProviderUserKey select x 
0
source

try this way

 List<Clinets> AllClinets =entityObject.Clinets .ToList(); Foreach( var check in AllClinets) { if(check.UserTable.RoleTable.RoleName=="Rolename1") { //This users are Rolename1 } else { //other. } } 
-1
source

A stored procedure would be better in this case.

-2
source

Source: https://habr.com/ru/post/952244/


All Articles