2015-10-14 95 views
0

我正在構建一個用於學習目的的Web應用程序,它將是一個多用戶應用程序。每個用戶將擁有他們的數據。我不是100%確定如何實現這一點。我應該讓Model1包含一個int UserId {get; set;}屬性來保存用戶GUID,還是應該是IdentityUser類型?然後在我的控制器中,我是否總是考慮當前登錄的用戶ID以查詢我的問題?我應該能夠從會話中獲取userId?多用戶應用程序

+1

似乎是一個很好的理由來使用'Asp.Net Identity' – Milen

回答

2

由於某些原因,用戶對象似乎被人嚇倒,但它與任何其他類型的關係沒有區別。是的,如果一個特定的實體由用戶「擁有」,那麼應該有一個用戶實體的外鍵。

我假設您已經使用ASP.NET身份,因爲您提到了IdentityUser,但您似乎對Entity Framework如何與關係一起工作感到困惑。從技術上講,下面的兩個屬性將會對生成的表相同的淨效應(例如一個名爲User_Id柱:

public string User_Id { get; set; } 

OR

public virtual ApplicationUser User { get; set; } 

在第二行中,實體框架看到你因爲它需要創建一個隱式外鍵來跟蹤這個關係,它不是你的實體的一部分,而是它在數據庫表上,因爲實體框架顯然不能存儲整個用戶對象位於數據庫級別的單個列中,您也不想要。

這就是說,你應該對關係使用的代碼實際上應該是這樣的:

[ForeignKey("User")] 
public string UserId { get; set; } 
public virtual ApplicationUser User { get; set; } 

這做了兩兩件事:

  1. 你得到一個導航屬性User,可以讓你直接訪問通過這個實體傳遞給用戶對象,同時通知實體框架在這裏需要跟蹤的實體之間存在關係。

  2. 您有一個明確的外鍵屬性UserId,它允許您在需要時真正獲得外鍵。如果您希望能夠執行諸如從選擇列表中選擇相關項目的操作,那麼這通常是必需的,因爲選擇列表只能發佈像int或字符串這樣的基本類型。如果你沒有這個屬性,這將是更難以實現這種情況。

技術上的ForeignKey屬性沒有嚴格要求,因爲實體框架將拿起UserIdUser按照慣例外鍵。不過,我認爲最好明確一下你期望的情況,並且在約定可能不恰當的情況下,使用ForeignKey的習慣將確保事情仍然按照他們應該的方式工作。

最後,關於授權,是的,你會過濾用戶的實體,以便每個用戶只看到他們應該看到什麼。例如:

var widgets = db.Widgets.Where(m => m.UserId == User.Identity.GetUserId()); 

或者,當你正在展示或允許用戶編輯單個項目的情況:

var widget = db.Widgets.SingleOrDefault(m => m.Id == widgetId && m.UserId == User.Identity.GetUserId()); 
if (widget == null) 
{ 
    return new HttpNotFoundResult(); 
} 

就這樣,用戶甚至沒有可視性什麼其他「小部件」可能在應用程序中。如果不是他們的,他們會得到一個404,就好像事件不存在一樣。

+0

那麼我的創建操作呢?我是否設置了UserId和User屬性? UserId沒有問題,但設置用戶屬性呢? – Chris

+0

其實你可以設置其中一個。這主要取決於你擁有的東西。如果你有一個id,但沒有用戶實例,那麼從數據庫中查找用戶只是爲了設置另一個實體的屬性是毫無意義的。只需設置ID,實體框架就可以解決問題。用戶實例反之亦然。雖然,你仍然可以通過'user.Id'設置id,或許你會發現直接設置用戶屬性會更容易。無論哪種方式,Entity Framework都會將其整理出來。 –

0

試着想想所有的情況。你認爲有共享登錄的可能性嗎?需要訪問而無需登錄或多次登錄的用戶也可能導致問題。在大多數情況下使用UserId是一個很好的解決方案,但要確保知道誰在使用它以及如何使用它。