Hybris Enterprise Commerce Platform 服務層的設計與實現

Hybris Enterprise Commerce Platform這個系列以前已經由個人同事,SAP成都研究院Hybris開發團隊的同事張健(Zhang Jonathan)發佈過兩篇文章了。這裏Jerry要特別感謝張健,儘管最近他的第二個孩子誕生了,工做之餘的生活變得更加忙碌,然而張健仍然抽出少的可憐的業餘時間完成了這個系列的第三篇文章。前端

前兩篇文章分別介紹了SAP Hybris的前端和DTO層:java

本文由張健繼續向咱們介紹SAP Hybris的持久層即Service層。下面是他的正文。數據庫

前兩篇文章分別介紹了SAP Hybris的前端和DTO層:框架

  • 從產品展現頁面談談Hybris的特有概念和設計結構
  • 從產品展現頁面談談Hybris系列之二: DTO, Converter和Populator

當咱們打開Hybris某個Product的明細頁面時,Hybris後臺執行了下面三步邏輯:spa

1. Service層從數據庫裏把數據取出,以Model(又稱爲DAO對象)的形式返回給Facade層。命令行

2. Facade層調用Converter, 在Populator的幫助下,基於Model生成了DTO。設計

3. Product明細頁面的Controller將其對應的JSP視圖路徑返回給Hybris框架,經過JSP技術繪製出最後的UI。code

其中步驟2和3已經在這個系列前兩篇文章介紹過,本文將詳細介紹上述步驟1。orm

Service層用XML定義的形式來管理Hybris的類型系統,既創建起與數據庫表的關聯,又將類型系統與具體的數據庫實現進行了隔離。Service層的ModelService和Flexible Search提供了便捷的增刪改查功能。讓咱們來一一瞭解。xml

Hybris類型系統

在DTO層的ProductFacade裏,調用了Service層中獲取ProductModel的方法以下。

很簡單的幾句代碼,和其餘常見的Java Web項目的Service很類似。那麼ProductModel是須要開發人員自行建立嗎?

應當注意ProductModel這樣的POJO類(Plain Old Java Object)不需開發人員自行建立,而是經過Hybris自有的類型系統生成的。

Hybris裏的類型分爲兩類,第一類是包含全部Hybris業務相關類型的ItemType(又稱ComposedType),Product便是這種類型。第二類是爲ItemType的集合屬性和關係屬性提供支持的DataType, 包括了 CollectionTypes, MapTypes, EnumerationTypes, RelationTypes 和 AtomicTypes。例如產品對應的多個媒體文件,就能夠用CollectionTypes來定義,而後再用RelationTypes和Product類型作關聯。

ABAP顧問們能夠把前者(ItemType)類比成ABAP Data Dictionary裏定義的包含了業務邏輯的全局數據類型,然後者就是ABAP裏用STANDARD, SORTED和HASHED TABLE等等將這些業務數據類型的一個聚合。而對於Java開發者來講, CollectionTypes, MapTypes這些類型其實就是Hybris對JDK中的List, Map等類型一個更高層次的抽象。

items.xml

和Hibernate框架使用XML定義類型和數據庫配置類似,Hybris類型系統的具體定義存在各個extension的items.xml文件裏。好比Product類型是存在於"../hybris/bin/platform/ext/core/resources"文件夾下的core-items.xml文件內。這個文件也定義了不少Hybris核心的業務類型。

咱們看一個實際的例子,即Product類型在items.xml中的定義。SAP Hybris的幫助文檔裏有items.xml裏每一個字段的詳細含義,這裏只介紹下圖中紅色高亮的字段。

extends: GenericItem。代表Product這個類型是在另外一個類型GenericItem基礎上作擴展。

GenericItem是根類型,至關於Java類型系統的java.lang.Object。Hybris類型系統經過繼承的方式避免了字段的重複建模。

假設咱們已經用上面展現的items.xml進行了Product的建模,如今有一個新的需求,定義CustomerProduct類型。從業務上說,CustomerProduct僅僅是在Product類型的基礎上增長一個字段用於維護Customer ID。ABAP顧問們會新建一個CustomerProduct的結構,把Product類型經過Include的方式添加到CustomerProduct中去,經過include的方式繼承前者上維護的全部字段,而後只需在CustomerProduct上定義一個新字段CUSTOMER_ID便可。

對於Hybris類型系統,思路相似,用CustomerProduct類型去extends Product類型,而後只需定義一個CustomerID字段便可。

autocreate = true: 在執行Hybris命令行ant initialize進行Hybris系統初始化時,根據items.xml的定義在數據庫表中建立對應的類型。

generate = true: 在ant編譯時生成該類型對應的POJO類。

以上圖的Product類型爲例,由於generate屬性設置爲true, 所以編譯以後,咱們能在下面的文件夾發現一個自動生成的POJO類,命名規範爲<類型名稱>Model.java:

hybrisinplatformootstrapgensrcdehybrisplatformcoremodelproduct

和ABAP不少自動生成的資源一般都放在名爲$GEN之類的包的套路同樣,POJO類所在的文件目錄中的gensrc,也提示了該文件是自動生成的。

打開ProductModel.java查看其內容,能進一步瞭解items.xml裏定義的屬性是如何映射到這個自動生成的POJO類的:items.xml裏定義的每個類型屬性,都會在POJO類裏自動生成一套set和get方法。

以name屬性爲例,在ProductModel.java裏自動生成的setName和getName:

table = Products: 數據庫對應的表名,在整個Hybris類型系統惟一存在。

attribute autocreate="true" qualifier="code" type="java.lang.String" generate="true":POLO類中會出現一個新的成員,名稱爲code,類型爲String,並帶有set和get方法,ant initialize時在數據庫表中建立該屬性。

ModelService

定義好類型後,就須要開發相應的增刪改查功能了。Hybris提供了de.hybris.platform.servicelayer.model.ModelService類做爲幫助類,只需傳入POJO類給對應方法,便可實現增刪改查功能。這和Hibernate裏的幫助類的用法是相似的。查詢操做對應get方法,建立和更新對應save方法,刪除操做則爲remove方法。還有saveAll和removeAll方法,只需傳入業務類型的集合便可實現批量增改或刪除。

下圖是一個例子,經過getModelService拿到ModelService實例,執行save操做。

Flexible Search

對於複雜查詢,Hybris也提供了本身的查詢語句Flexsible Search。如ProductDao中使用的關聯Category類型的查詢:

用過ADBC和JDBC的ABAP顧問和Java開發者,對上面的代碼必定不會陌生。

下面是從Jerry的博客裏摘出來的一張圖,ADBC和JDBC的對比:

https://blogs.sap.com/2017/05...

Hybris支持主流數據庫,包括MySQL,Oracle,SQL Server及SAP HANA數據庫等等。而Flexible Search概念的引入,思路相似ABAP Open SQL,經過編寫不依賴於任何具體數據庫提供商的Flexible Search代碼,將Hybris應用層同底層數據庫的具體實現作了解耦。而上面的語句中,POJO類裏如ProductModel._TYPECODE 的值就是「Product」,是編譯時自動生成的。所以查詢語句可轉譯成以下文本:

問號後面的」Category「是要傳入查詢語句的參數名,這裏即爲傳入了方法的參數「CategoryModel」。

到這裏Hybris的Service層就基本介紹完了,而Hybris概要的系列文章也告一段落。但願你們經過這些文章對Hybris Enterprise Commerce Platform有必定的認識。感謝閱讀。

要獲取更多Jerry的原創技術文章,請關注公衆號"汪子熙"或者掃描下面二維碼:

相關文章
相關標籤/搜索