2013-07-20 40 views
0

我是一個春季範圍的新手。彈簧控制器範圍和存儲會話數據

我有一個這樣的代碼如下

@Controller 
    public class PageController extends AbstractController { 

private ABCManager abcManager;// repository singleton bean. 

@Inject 
public PageController(final ABCManager accountDiaryManager){ 
    this.abcManager= abcManager; 
} 

    @RequestMapping(value="/createpage",method=RequestMethod.POST) 
public @ResponseBody Page createPage(@RequestParam(value="viewtype")final String viewtype, final WebRequest request) 
    { 
    final ABC abc= (abc) request.getAttribute(AbstractController.CURRENT_ABC, WebRequest.SCOPE_SESSION); 

     ......... 
     abcManager.createPage(Long.valueOf(abc.getId()), page); 
request.setAttribute("abc", abcManager.getabc(abc.getId()),WebRequest.SCOPE_SESSION); 
} 

由於ABC對象可以在同一個用戶會話中更改多次爲abc是根對象,包含樹形結構和用戶的行動將在子對象的任何地方涉及變革。因此,當執行編輯時,我將修改過的abc對象保存在請求中,以便每次在請求中都可以使用最新的abc對象。這個abc可能會變得非常大,這是我的擔憂。這是做這種事的好方法嗎?

我想知道這是否是一種很好的做法來編寫這樣的代碼。這是一個線程安全的方式嗎?什麼是最好的替代可用。

回答

0
  1. 獲取/放入會話對象不是線程安全的。在你的情況下,因爲你在會話中存儲與特定用戶相關的數據,所以只要你不希望同一用戶執行多個可以同時更新會話的動作,就可以這樣做。話雖如此,如果您真的正在開發一個生產就緒系統,並且在這種情況下您最終將擁有多個應用程序服務器,那麼您需要考慮會話管理的策略 - 您可以在web服務器上使用粘性會話(Apache httpd例如),以便屬於同一個會話的所有請求都被轉發到同一個應用服務器,或者您需要在應用服務器之間啓用會話複製。

  2. ABC增長很大需要量化。如果您認爲它增長到1MB大小,並且已經爲您的應用服務器的JVM分配了2 GB RAM,並且假設1 GB可用於應用程序的內存需求,那麼您可以存儲多達1000個用戶的數據。根據您計劃支持的併發會話數量,您將不得不配置適量的RAM。

  3. 如果ABC存儲瞬態數據,例如購物車信息,並且在服務器重新啓動期間您可以丟失哪些數據,那麼您的方法沒問題。如果您不想丟失數據,那麼可以考慮使用緩存系統或NoSQL存儲的鍵值類型(CouchBase,Redis等)。 RDBMS也是一種選擇,但它實際上取決於您試圖在會話中維護的數據的性質,以及它們是否真的具有會話語義,或者您只是將它們存儲在會話中以方便起見。