參考這篇
張小呆的碎碎唸
稍微改成log到資料庫並記錄下當時所處理的資料.
public class LogActionFilterAttribute : ActionFilterAttribute
{
public string ControllerName { get; set; }
public string ActionName { get; set; }
private ApplicationDbContext db = new ApplicationDbContext();
public override void OnActionExecuting(ActionExecutingContext filterContext)
{
string uid = filterContext.HttpContext.User.Identity.Name.ToString();
string originController = filterContext.RouteData.Values["controller"].ToString();
string originAction = filterContext.RouteData.Values["action"].ToString();
string originArea = String.Empty;
if (filterContext.RouteData.DataTokens.ContainsKey("area"))
originArea = filterContext.RouteData.DataTokens["area"].ToString();
//這邊利用傳遞參數的名稱來判定要如取出相關資料與以記錄, 所以Action的參數名稱就必須要有可鑑別性
string result = "";
if (filterContext.ActionParameters.ContainsKey("empv"))
{
empEditViewModels viewModel = (empEditViewModels)filterContext.ActionParameters["empv"];
result = viewModel.emp1.eid + viewModel.emp1.cname + " 職稱: " + viewModel.emp1.title + " 部門編號: " + viewModel.emp1.dept;
};
if (filterContext.ActionParameters.ContainsKey("emp"))
{
emp emp1 = (emp)filterContext.ActionParameters["emp"];
result = emp1.eid + emp1.cname + " 職稱: " + emp1.title + " 部門編號: " +emp1.dept;
};
if (filterContext.ActionParameters.ContainsKey("id"))
{
int id1 = (int)filterContext.ActionParameters["id"];
result = " 序號: " + id1.ToString();
};
//紀錄相關資料到資料庫
actlog logmodel = new actlog()
{
App = ControllerName+originController,
Act = ActionName+originAction,
Pepo = String.IsNullOrEmpty(SessionHelper.RealName) ? uid : SessionHelper.RealName,
Ext ="進入網頁 : "+result,
Tm = DateTime.Now
};
db.actlogs.Add(logmodel);
db.SaveChanges();
}
public override void OnActionExecuted(ActionExecutedContext filterContext)
{
}
public override void OnResultExecuting(ResultExecutingContext filterContext)
{
}
public override void OnResultExecuted(ResultExecutedContext filterContext)
{
string uid = filterContext.HttpContext.User.Identity.Name.ToString();
actlog logmodel = new actlog()
{
App = ControllerName,
Act = ActionName,
Pepo = String.IsNullOrEmpty(SessionHelper.RealName) ? uid : SessionHelper.RealName,
Ext = "傳回的動作結果執行完成",
Tm = DateTime.Now
};
db.actlogs.Add(logmodel);
db.SaveChanges();
}
}
在control中使用範例 :
[HttpPost]
[ValidateAntiForgeryToken]
[LogActionFilter(ControllerName = "員工資料管理", ActionName = "新增完成")]
public ActionResult Create([Bind(Include = "id,eid,cname,dept,title")] emp emp, int? page, int? itemsPerPage, string sortOrder, string currentFilter)
{
ViewBag.DropDownList = new SelectList(db.deps, "Id", "title");
ViewBag.CurrentPage = page;
ViewBag.CurrentItemsPerPage = itemsPerPage;
ViewBag.OldSortParm = sortOrder;
ViewBag.CurrentFilter = currentFilter;
if (ModelState.IsValid)
{
db.emps.Add(emp);
db.SaveChanges();
return RedirectToAction("Index", new { page = ViewBag.CurrentPage, itemsPerPage = ViewBag.CurrentItemsPerPage, sortOrder = ViewBag.OldSortParm, searchString = "", CurrentFilter = ViewBag.CurrentFilter });
}
return View(emp);
}
紀錄結果 :
2014年8月19日 星期二
在authentication mode="Forms"下使用 membership defaultProvider="ADMembershipProvider", 搭配Fluent Security的測試及如何使用AD群組來做權限控管
參考這篇,
Fluent Security - 在MVC集中管理頁面權限的套件
真的不錯用, 但受到Form登入無法直接使用 AD的群組當Roles的影響.
所以只能用上
configue.ForAllControllers().Ignore();
configue.For<HomeController>().DenyAnonymousAccess();
configue.For<HomeController>().DenyAuthenticatedAccess();
而一直找不到使用角色的辦法..
configue.For<HomeController>(hc => hc.Contact()).RequireAnyRole("Everyone");
只好回頭用自訂 action filter的辦法來處理 AD的Group.
1.加入參考
C:\Program Files\Reference Assemblies\Microsoft\Framework\.NETFramework\v4.5\System.DirectoryServices.AccountManagement.dll
2. Using System.DirectoryServices.AccountManagement;
3.使用者登入時取回AD Group資料塞入Session, 給自訂Action Filter及View使用.
[HttpPost]
public ActionResult Login(LoginModel model, string returnUrl)
{
if (!this.ModelState.IsValid)
{
return this.View(model);
}
if (Membership.ValidateUser(model.UserName, model.Password))
{
//取回AD Group資料塞入Session
var context = new PrincipalContext(ContextType.Domain, "Adimmune");
var userPrincipal = UserPrincipal.FindByIdentity(context,
IdentityType.SamAccountName,
model.UserName);
var UGS = userPrincipal.GetAuthorizationGroups();
string uGroup = "";
foreach (var ug in UGS)
uGroup = uGroup + ug.Name + ";";
SessionHelper.UserGroup = uGroup;
FormsAuthentication.SetAuthCookie(model.UserName, model.RememberMe);
if (this.Url.IsLocalUrl(returnUrl) && returnUrl.Length > 1 && returnUrl.StartsWith("/")
&& !returnUrl.StartsWith("//") && !returnUrl.StartsWith("/\\"))
{
return this.Redirect(returnUrl);
}
return this.RedirectToAction("Index", "Home");
}
this.ModelState.AddModelError(string.Empty, "您提供的Windows帳號或密碼並不正確,如有疑問請與資訊人員聯絡.");
return this.View(model);
}
//!!切記要在LogOff時清空SessionHelper.UserGroup,否則會影響權限控管
public ActionResult LogOff()
{
SessionHelper.UserGroup = "";
SessionHelper.RealName = "";
FormsAuthentication.SignOut();
return this.RedirectToAction("Index", "Home");
}
4.自訂Action Filter.
public class AuthorizeADAttribute : AuthorizeAttribute
{
public string Groups { get; set; }
protected override bool AuthorizeCore(HttpContextBase httpContext)
{
/* Return true immediately if the authorization is not
locked down to any particular AD group */
if (String.IsNullOrEmpty(Groups))
return true;
// Get the AD groups
var groups = Groups.Split(',').ToList<string>();
// Verify that the user is in the given AD group (if any)
foreach (var group in groups)
if (SessionHelper.UserGroup.Contains(group+";"))
return true;
return false;
}
5. Control使用範例
[AuthorizeAD(Groups = "IT")]
public class empsController : Controller
{
..................................
}
6 View使用範例
if (Session["UserGroup"].ToString().Contains("webAdmin01;"))
{
<ul class="nav pull-right">
<li class="dropdown">
<a href="#" class="dropdown-toggle" data-toggle="dropdown">後台管理<b class="caret"></b></a>
<ul class="dropdown-menu">
<li><a href="@Url.Action("Index", "emps")"><i class="icon-off"></i>員工</a></li>
<li><a href="@Url.Action("Index", "deps")"><i class="icon-off"></i>部門</a></li>
<li><a href="@Url.Action("Index", "exms")"><i class="icon-off"></i>評核類別</a></li>
<li><a href="@Url.Action("Index", "ots")"><i class="icon-off"></i>評核時間</a></li>
<li><a href="@Url.Action("Index", "ts")"><i class="icon-off"></i>評核紀錄</a></li>
<li><a href="@Url.Action("Index", "actlogs")"><i class="icon-off"></i>Logs</a></li>
</ul>
</li>
</ul>
}
Fluent Security - 在MVC集中管理頁面權限的套件
真的不錯用, 但受到Form登入無法直接使用 AD的群組當Roles的影響.
所以只能用上
configue.ForAllControllers().Ignore();
configue.For<HomeController>().DenyAnonymousAccess();
configue.For<HomeController>().DenyAuthenticatedAccess();
而一直找不到使用角色的辦法..
configue.For<HomeController>(hc => hc.Contact()).RequireAnyRole("Everyone");
只好回頭用自訂 action filter的辦法來處理 AD的Group.
1.加入參考
C:\Program Files\Reference Assemblies\Microsoft\Framework\.NETFramework\v4.5\System.DirectoryServices.AccountManagement.dll
2. Using System.DirectoryServices.AccountManagement;
3.使用者登入時取回AD Group資料塞入Session, 給自訂Action Filter及View使用.
[HttpPost]
public ActionResult Login(LoginModel model, string returnUrl)
{
if (!this.ModelState.IsValid)
{
return this.View(model);
}
if (Membership.ValidateUser(model.UserName, model.Password))
{
//取回AD Group資料塞入Session
var context = new PrincipalContext(ContextType.Domain, "Adimmune");
var userPrincipal = UserPrincipal.FindByIdentity(context,
IdentityType.SamAccountName,
model.UserName);
var UGS = userPrincipal.GetAuthorizationGroups();
string uGroup = "";
foreach (var ug in UGS)
uGroup = uGroup + ug.Name + ";";
SessionHelper.UserGroup = uGroup;
FormsAuthentication.SetAuthCookie(model.UserName, model.RememberMe);
if (this.Url.IsLocalUrl(returnUrl) && returnUrl.Length > 1 && returnUrl.StartsWith("/")
&& !returnUrl.StartsWith("//") && !returnUrl.StartsWith("/\\"))
{
return this.Redirect(returnUrl);
}
return this.RedirectToAction("Index", "Home");
}
this.ModelState.AddModelError(string.Empty, "您提供的Windows帳號或密碼並不正確,如有疑問請與資訊人員聯絡.");
return this.View(model);
}
//!!切記要在LogOff時清空SessionHelper.UserGroup,否則會影響權限控管
public ActionResult LogOff()
{
SessionHelper.UserGroup = "";
SessionHelper.RealName = "";
FormsAuthentication.SignOut();
return this.RedirectToAction("Index", "Home");
}
4.自訂Action Filter.
public class AuthorizeADAttribute : AuthorizeAttribute
{
public string Groups { get; set; }
protected override bool AuthorizeCore(HttpContextBase httpContext)
{
/* Return true immediately if the authorization is not
locked down to any particular AD group */
if (String.IsNullOrEmpty(Groups))
return true;
// Get the AD groups
var groups = Groups.Split(',').ToList<string>();
// Verify that the user is in the given AD group (if any)
foreach (var group in groups)
if (SessionHelper.UserGroup.Contains(group+";"))
return true;
return false;
}
5. Control使用範例
[AuthorizeAD(Groups = "IT")]
public class empsController : Controller
{
..................................
}
6 View使用範例
if (Session["UserGroup"].ToString().Contains("webAdmin01;"))
{
<ul class="nav pull-right">
<li class="dropdown">
<a href="#" class="dropdown-toggle" data-toggle="dropdown">後台管理<b class="caret"></b></a>
<ul class="dropdown-menu">
<li><a href="@Url.Action("Index", "emps")"><i class="icon-off"></i>員工</a></li>
<li><a href="@Url.Action("Index", "deps")"><i class="icon-off"></i>部門</a></li>
<li><a href="@Url.Action("Index", "exms")"><i class="icon-off"></i>評核類別</a></li>
<li><a href="@Url.Action("Index", "ots")"><i class="icon-off"></i>評核時間</a></li>
<li><a href="@Url.Action("Index", "ts")"><i class="icon-off"></i>評核紀錄</a></li>
<li><a href="@Url.Action("Index", "actlogs")"><i class="icon-off"></i>Logs</a></li>
</ul>
</li>
</ul>
}
訂閱:
文章 (Atom)