我有几个关于 MVC 应用程序中的逻辑位置的问题。
这是控制器中的一个示例操作,想知道这是否逻辑过多,如果是,您还会把它放在哪里:
仅供参考 -Manager
是一种服务类型层,我们将 BO 转换为 DTO/ViewModels 来回转换到另一个执行我们 BL 的层
Public Function ChangeClaim(model As ChangeClaimViewModel) As ActionResult
Manager.SetClaimNumber(model.ClaimNumber)
Dim securityToken = Manager.ClaimSecurityToken
If (securityToken.ValidClaim) Then
Session("ClaimNumber") = model.ClaimNumber
If (Not securityToken.ConflictAccess) Then
ModelState.AddModelError("ClaimNumber", "You do not have access to this claim.")
End If
Else
ModelState.AddModelError("ClaimNumber", "Invalid claim number.")
End If
If (Not ModelState.IsValid) Then
Return View(Manager.GetViewModel())
End If
If (model.URL.Contains("ChangeClaim") OrElse model.URL.Contains("EnterClaim")) Then
model.URL = Url.Action("Index", "Home")
End If
Return Redirect(model.URL)
End Function
另外,我会假设挂起bool
ViewModel 以在视图中执行类似这样的逻辑可以吗?
@if (Model.HasExposureAccess)
{
<li><a href="#tab-pane-2">@Model.Labels.Reimbursements</a></li>
}
还有其他改进建议吗?
哦,对不起 VB 和 C# 的混合,我工作的商店除了 VB 中的视图之外什么都做,我不得不努力争取在 C# 中做视图!!??
编辑#1
因此,If (securityToken.ValidClaim) Then
让我尽我所能为您介绍整个过程,看看您是否有任何建议。
当用户尝试更改索赔编号时,它进入模型,传递给Manager.SetClaim
方法(管理器是我们创建的一种服务层,能够使用我们现有的 BO 框架,别笑, 是 CSLA.NET V1 的一个经过大量修改的版本,它们是非常紧密耦合的对象,因为 BL 和 DAL 都存在于对象内部。根本不是我的选择,但是你做什么:)) 验证它是一个有效的声明,并且用户可以访问它。我正在尽我最大的努力使图层尽可能地分开:
1) MVC 应用程序
2) 应用程序管理器
3) 现有 BOF
我说的有道理吗?
编辑#2
因此,我将控制器操作中的逻辑放入了一个操作过滤器中,如下所示:
Public Class ValidateClaimAttribute
Inherits ActionFilterAttribute
Public Overrides Sub OnActionExecuting(filterContext As System.Web.Mvc.ActionExecutingContext)
MyBase.OnActionExecuting(filterContext)
Dim model As ChangeClaimViewModel = CType(filterContext.ActionParameters("model"), ChangeClaimViewModel)
Dim manager As IInjuredWorkerManager = DependencyResolver.Current.GetService(Of IInjuredWorkerManager)()
Dim securityToken = manager.ClaimSecurityToken
manager.SetClaimNumber(model.ClaimNumber)
If (securityToken.ValidClaim) Then
filterContext.HttpContext.Session("ClaimNumber") = model.ClaimNumber
If (Not securityToken.ConflictAccess) Then
filterContext.Controller.ViewData.ModelState.AddModelError("ClaimNumber", "You do not have access to this claim.")
End If
Else
filterContext.Controller.ViewData.ModelState.AddModelError("ClaimNumber", "Invalid claim number.")
End If
End Sub
End Class
<ValidateClaim()>
Public Function ChangeClaim(model As ChangeClaimViewModel) As ActionResult
If (Not ModelState.IsValid) Then
Return View(Manager.GetViewModel())
End If
If (model.URL.Contains("ChangeClaim") OrElse model.URL.Contains("EnterClaim")) Then
model.URL = Url.Action("Index", "Home")
End If
Return Redirect(model.URL)
End Function
这看起来更像是正确的做法吗?
编辑#3 因此,我对此进行了进一步优化:
<ValidateClaim()>
Public Function ChangeClaim(model As ChangeClaimViewModel) As ActionResult
If (Not ModelState.IsValid) Then
Return View(Manager.GetViewModel())
End If
Return New MyRedirect(model.URL)
End Function
Public Class ValidateClaimAttribute
Inherits ActionFilterAttribute
Public Overrides Sub OnActionExecuting(filterContext As System.Web.Mvc.ActionExecutingContext)
MyBase.OnActionExecuting(filterContext)
Dim model As ChangeClaimViewModel = CType(filterContext.ActionParameters("model"), ChangeClaimViewModel)
Dim manager As IInjuredWorkerManager = DependencyResolver.Current.GetService(Of IInjuredWorkerManager)()
Dim securityToken = manager.ClaimSecurityToken
manager.SetClaimNumber(model.ClaimNumber)
If (securityToken.ValidClaim) Then
filterContext.HttpContext.Session("ClaimNumber") = model.ClaimNumber
If (Not securityToken.ConflictAccess) Then
filterContext.Controller.ViewData.ModelState.AddModelError("ClaimNumber", "You do not have access to this claim.")
End If
Else
filterContext.Controller.ViewData.ModelState.AddModelError("ClaimNumber", "Invalid claim number.")
End If
End Sub
End Class
Public Class MyRedirect
Inherits ActionResult
Private _url As String
Public Sub New(url As String)
_url = url
End Sub
Public Overrides Sub ExecuteResult(context As System.Web.Mvc.ControllerContext)
Dim urlHelper As New UrlHelper(context.RequestContext)
If (_url.Contains("ChangeClaim") OrElse _url.Contains("EnterClaim")) Then
_url = urlHelper.Action("Index", "Home")
End If
context.HttpContext.Response.Redirect(_url)
End Sub
End Class
完整的控制器代码:
Imports System.Web.Mvc
Imports System.Security.Principal
Imports Telerik.Web.Mvc
Imports System.Globalization
Namespace Controllers
<HandleException(View:="Error")>
<OutputCache(Duration:=0)>
Public MustInherit Class InjuredWorkerController
Inherits SAIF.Web.Mvc.Framework.Controllers.ContextController
Public Property Manager As IInjuredWorkerManager
Public Sub New(manager As IInjuredWorkerManager)
_Manager = manager
_Manager.ValidationDictonary = New ModelStateWrapper(ModelState)
End Sub
<ValidateClaim()>
Public Function ChangeClaim(model As ChangeClaimViewModel) As ActionResult
If (Not ModelState.IsValid) Then
Return View(Manager.GetViewModel())
End If
Return New MyRedirect(model.URL)
End Function
Public Function SetCulture(culture As String, returnUrl As String) As ActionResult
Response.Cookies.Add(New HttpCookie("culture") With {
.Value = culture,
.Expires = DateTime.Now.AddYears(1)
})
Return Redirect(returnUrl)
End Function
Protected Overrides Sub ExecuteCore()
Dim cultureName = "en-US"
Dim cultureCookie = Request.Cookies("culture")
If (cultureCookie IsNot Nothing) Then
cultureName = Request.Cookies("culture").Value
End If
Threading.Thread.CurrentThread.CurrentCulture = CultureInfo.CreateSpecificCulture(cultureName)
Threading.Thread.CurrentThread.CurrentUICulture = CultureInfo.CreateSpecificCulture(cultureName)
MyBase.ExecuteCore()
End Sub
Protected Overrides Sub OnActionExecuting(filterContext As System.Web.Mvc.ActionExecutingContext)
MyBase.OnActionExecuting(filterContext)
Dim controller = filterContext.RouteData.Values("controller").ToString
Dim action = filterContext.RouteData.Values("action").ToString
If (action.ToLower = "enterclaim" OrElse action.ToLower = "changeclaim") Then
Return
Else
Dim claimNumber As String = String.Empty
Dim workerID As Decimal
If (Session("ClaimNumber") IsNot Nothing) Then
claimNumber = Session("ClaimNumber").ToString
End If
If (Session("WorkerID") IsNot Nothing) Then
workerID = CDec(Session("WorkerID"))
End If
If (String.IsNullOrEmpty(claimNumber)) Then
If (workerID = 0) Then
If (Manager.IsExternalUser) Then
workerID = Manager.GetWorkerIdByDomainUser
claimNumber = Manager.GetMostRecentClaimNumber(workerID)
Else
filterContext.Result = New RedirectResult("/MyClaim/Home/EnterClaim")
End If
End If
End If
Manager.SetClaimNumber(claimNumber)
End If
End Sub
Public Function SendMessage(<Bind(prefix:="SendMessage")> model As IWSendMessageViewModel) As ActionResult
Manager.SendAdjusterEmail(model.AdjusterEmail, model.PersonEmail, "IW Contact Message", model.Message, model.SendCopyToSender)
Return Json(New With {.message = "Success"}, "application/json")
End Function
End Class
End Namespace