2011-11-06 48 views
0

我正在玩一些代碼,並且需要關於一些項目的意見。 我需要從認證服務返回一個用戶對象回我的控制器,通過Ninject注入控制器。所以每個人都在同一頁面上。這裏是控制器代碼以及一些服務代碼。MVC 3/C#總體設計意見

在登錄ActionResult中,我檢查用戶是否存在,如果他們這樣做,我將使用身份驗證服務對他們進行身份驗證。好吧,很簡單,它返回true | false。我還希望用戶可以做更多的事情,我已經打到數據庫,爲什麼回去再打一次。正如你在驗證服務中看到的,我已經設置了一個很好的用戶對象。

現在最大的問題!!!我應該返回用戶還是IUser?我的想法....我不希望我的控制器取決於具體的用戶,所以我想通過ninject和ctor Inject Iuser將IUser連接到用戶。然後我可以設置_user = _authenticationService.AuthenticateUser(userName,password);

好,壞醜?想法???

控制器代碼:

public class UsersController : Controller 
{ 
    private readonly IUserService _userService; 
    private readonly IAuthenticationService _authenticationService; 

    public UsersController(IUserService userService,IAuthenticationService authenticationService) 
    { 
     _userService = userService; 
     _authenticationService = authenticationService; 
    } 

    public ActionResult Login() 
    { 
     return View(); 
    } 
    [HttpPost] 
    public ActionResult Login(UserLoginViewModel userLoginViewModel) 
    { 
     string userName = userLoginViewModel.UserName; 
     string password = userLoginViewModel.Password; 

     if (_userService.UserExists(userName)) 
     { 
     //This will change 
      if (_authenticationService.AuthenticateUser(userName, password)) 
      { 

      } 
     } 


     return PartialView("_Login"); 
    } 

    public ActionResult Register() 
    { 
     return PartialView("_Register"); 
    } 
    [HttpPost] 
    public ActionResult Register(UserRegisterViewModel userRegisterViewModel) 
    { 
     ModelState.AddModelError("UserName", "Testing"); 
     return PartialView("_Register"); 
    } 
} 

服務代碼:

public class AuthenticationService:IAuthenticationService 
{ 
    private readonly IRepository _repository; 
    private readonly IEncryption _encryption; 

    public AuthenticationService(IRepository repository,IEncryption encryption) 
    { 
     _repository = repository; 
     _encryption = encryption; 
    } 

    // HMM! Ok I need to get the User object back to the controller, so instead of returning bool should I return User or IUser. 

    public bool AuthenticateUser(string userName, string password) 
    { 
     try 
     { 
      var user = _repository.Select<Users>().Where(u => u.UserName == userName).Select(u => new User 
      { 
       UserId = u.UserID, 
       UserTypeId = u.UserTypeID, 
       UserName = u.UserName, 
       Password = u.Password, 
       Salt = u.Salt, 
       ActivationCode = u.ActivationCode, 
       InvalidLoginAttempts = u.InvalidLoginAttempts, 
       IsLockedOut = u.IsLockedOut, 
       LastLoginDate = u.LastLoginDate, 
       Active = u.Active, 
       DateCreated = u.DateCreated, 
       LastUpdated = u.LastUpdated 
      }).Single(); 

      // Check the users password hash 
      if(_encryption.VerifyHashString(password,user.Password,user.Salt)) 
      { 
       return true; 
      } 
     } 
     catch (Exception) 
     { 
      return false; 

     } 
     // get the user from the database 




     return false; 
    } 
} 
+0

您的用戶類型沒有任何邏輯(我的意思是,它沒有方法)所以,爲什麼要使用接口IUser隔離它?這是所有類型的用戶都應簽署的合同? 我認爲你的服務必須檢索用戶類型,而不是IUser類型。 – lontivero

+0

AuthenticationService從存儲庫創建/檢索用戶。我只需要將User對象返回給控制器。 – CrazyCoderz

+0

簡單地返回IQueryable是可以接受的/可能的 – CrazyCoderz

回答

1

我只希望查找的User的名字,並與bool AuthenticateUser(User user, string password)檢查密碼。或者,如果你喜歡輸出參數,就像bool AuthenticateUser(string username, string password, out User user)一樣。我認爲UserExists方法在這種情況下沒有用處,因爲您想要更多地使用該對象。

0

我覺得這個其他後開始回答你的問題:

Why not use an IoC container to resolve dependencies for entities/business objects?

本質上,它說,你可以使用工廠模式而不是使用DI。

我也親自補充說我以前在Ninject郵件列表中看到過這樣的批評,在那裏提到總是通過DI解析實體時存在性能問題。基本上可能有很多創建引用不同服務和UI等中的每個實體;更不用說類型轉換了;你的應用程序以死亡的形式受到了一百萬次的削減(即它只是經常解決界面,性能成爲問題)。即使它現在不是性能問題,但我確定您希望您的應用程序在未來保持可擴展性。

爲了解決DI性能問題,您將嘗試將您的架構重新引導至面向工廠的設計。因此,這意味着工廠可能是首選的最佳人選,而不是用DI來解決實體(除非有這樣做的冒險理由,這可能不存在)。

總結:

  • 你可能不應該有IUSER在您的應用程序的接口。你的實體不應該有任何邏輯,所以實際類型實際上就是你正在使用的合約。

  • 對實體使用工廠,否DI。這會給性能和性能帶來可擴展性。

  • DI仍然有用,但不建議 爲實體,除非有一個強有力的理由(不能想到一個很好的理由我的頭頂)。

  • 通常DI將被用於推銷需要合同的合同。合同隱含在User類中,因爲它不應包含任何邏輯,而作爲服務確實包含邏輯並且將成爲DI的絕佳選擇。與用戶實體不同的是,我可以對它進行子類化並創建不同的用戶類型,並且用戶類仍然有用地被覆蓋,屬性等被重用,仍然支持外部合同。有了服務,我不想要一個具體的依賴關係,因爲我們不得不重寫服務上的所有方法,因爲它們通常不會有任何代碼共享,並且我可能不會從現有服務中獲得任何重用如果我要寫一個新的實現。

+0

IUser是DTO不是實體 – CrazyCoderz