4.1.1. Các thành phần chính của OFBiz
Download Ofbiz tại đây : http://ofbiz.apache.org/download.html
Sau khi download và giải nén chúng ta sẽ có một folder OFBiz. Trước tiên chúng ta xem các thành phần trong thư mục này.
Trong đó nội dung từng thành phần như sau :
.svn folder : Bao gồm các thông tin update hàng tuần của framework OFBiz và các ứng dụng .
application folder : Bao gồm các ứng dụng có trong OFBiz, khi chúng ta tự tạo một ứng dụng riêng, chúng ta nên đặt nó trong thư mục application hoặc đặt trong thư mục hot-deploy.
38
framework folder : Bao gồm các thành phần của framework OFBiz, giống như Entity Engine, Service Engine, thư mục chứa các file chung cho tất cả mọi ứng dụng.
hot-deploy folder : Trong thư mục này có thể có một số folder, nơi các thành phần của ứng dụng được tải tự động mà không cần tải chúng một cách rõ ràng như chúng ta vẫn thấy ở một số ứng dụng khác đặt trong Application folder.
specialpurpose folder : Bao gồm một số ứng dụng bổ sung như “ecommerce” và “workflow”, tuy nhiên chúng không phải một phần của OFBiz core.
themes folder : Bao gồm các file có chức năng thay đổi giao diện người dùng khi chạy OFBiz.
startobfiz.bat : File này được dùng khi chạy OFBiz.
4.1.2. Các thành phần trong Humanres
Tiếp theo chúng ta sẽ quan tâm đến một ứng dụng cụ thể. Trong trường hợp này chúng ta nghiên cứu tới ứng dụng Humanres.
Nhưng trước đó chúng ta cần chú ý đến file component-load.xml trong thư mục Application do file này có ý nghĩa rất quan trọng. Bởi vì khi không có nó thì OFBiz không thể load được bất cứ ứng dụng nào, trừ khi ứng dụng đó được đặt trong thư mục hot-deploy. Do đó khi tạo một ứng dụng mới chúng ta phải add thư
39
mục bên trong để báo cho OFBiz biết, việc này được làm với file component- load.xml – định nghĩa vị trí các ứng dụng.
ofbiz- component.xml : Định nghĩa ứng dụng bằng cách xác định vị trí của nó
- Data model : <entity-resource>
- Business logic : <service-resource>
- Web application : <webapp>
build.xml : Giống như tên của nó, file dùng để cho chương trình ant cách built ứng dụng OFBiz.
.svn folder : Chứa các lần update hàng tuần của ứng dụng.
build folder : Chứa code biên dịch Java “.class” file và các thư viện cho ứng dụng humanres.
config folder : Thường được sử dụng cho data configuaration,ví dụ nó được dùng để hỗ trợ các giao diện ngôn ngữ, bên trong nó chúng ta sẽ tìm được một số file cho các ngôn ngữ khác nhau, và dựa trên ngôn ngữ giao diện người dùng, một trong số các file này sẽ được sử dụng.
data folder : Chứa đựng dữ liệu load về khi OFBiz được khởi động và dữ liệu demo.
Cuối cùng là 2 thành phần entitydef và servicedef đều có 2 thành phần : definition và implementation
<component-loader xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="http://ofbiz.apache.org/dtds/component- loader.xsd">
<load-component component-location="commonext"/><!-- common component used by most other components -->
<load-component component-location="party"/> <load-component component-location="securityext"/> <load-component component-location="content"/> <load-component component-location="workeffort"/> <load-component component-location="product"/> <load-component component-location="manufacturing"/> <load-component component-location="accounting"/> <load-component component-location="humanres"/> <load-component component-location="order"/> <load-component component-location="marketing"/> </component-loader>
40
entitydef folder : chứa việc thực thi lớp dữ liệu, ví dụ bản quan hệ CSDL và các mối quan hệ. Bên trong thư mục này có 2 file chính, 1 cho việc định nghĩa và 1 cho việc thực thi : entitygroup.xml và entitymodel.xml
servicedef folder : Định nghĩa các service được dùng trong lớp business logic, nó chứa các file service.xml – định nghĩa services, service_view.xml – dùng cho view.
( Chú ý: Khi add 1 file service, cần phải được định nghĩa thêm trong ofbiz component.xml )
script folder : Chứa đựng việc thực thi cho các service sử dụng OFBiz mini- language và nó chứa đựng một số script. Bên trong thư mục này còn chứa việc thực thi các service cho các ứng dụng khác nhau
src folder : Chứa các file source cho các service – các file được thực thi với Java.
widget folder : Là lớp trình diễn OFBiz gần nhất,các trang được định nghĩa như “screen”. thư mục widgets cho giao diện màn hình người dùng. OFBiz cho phép thiết kế giao diện người dùng để tạo như “generic screens” có thể được sử dụng cho những nền khác. Nội dung thư mục widget phản ánh những thứ trên webapp. Do đó mỗi ứng dụng sẽ có màn hình riêng của nó. Screen được chia làm 2 phần : action và widget. Action chịu trách nhiệm cho việc lấy dữ liệu về trong khi widget chịu trách nhiệm hiển thị dữ liệu.
webapp folder : Chứa các form và ứng dụng web. Với OFBiz các trang được chia thành các thành phần nhỏ hơn, những cái được kết hợp để tạo lên sản phẩm mới. Do đó nhiều trang có thể chia sẻ các thành phần chung như header, sidebar, và navigation bars.
4.1.3. Chạy các ứng dụng trên OFBiz
Phần này tưởng rằng như dễ dàng như việc cài đặt và chạy một ứng dụng mà ta thường down trên Internet. Tuy nhiên, khi bắt tay vào việc thì ta mới gặp rất nhiều khó khăn như MyEclipse không đặt đúng địa chỉ của một số file, khi cho dịch Ofbiz từ cửa sổ Ant (build) thì báo lỗi file build.xml. Nếu mở file build.xml thì ta cũng không biết sửa chỗ nào vì nó báo lỗi ở một dòng thì thực ra lỗi lại xảy ra ở dòng khác.
41
Ví dụ 1: chương trình dịch báo lỗi ở dòng
<javac debug="on" deprecation="on" destdir="${build.dir}/classes">
Thì thực ra là lỗi ở dòng
<fileset dir="../../common/build/lib" includes="*.jar"/>
Ta sửa lại bằng cách thêm vào từ framework như sau:
<fileset dir="../../framework/common/build/lib" includes="*.jar"/>
Ví dụ 2: Ofbiz báo thiếu file khi Ofbiz không tìm thấy file trong thư mục ofbiz, mà nó chỉ mặc định trên ổ đĩa C:\Ofbiz\.... nhưng do ta đặt thư mục Ofbiz trong D:\workPlace\Ofbiz\... thì ta phải vào file .classpath để sửa lại các đường dẫn sai cho nó.
4.2. Các bước triển khai 4.2.1. Việt hóa Humanres 4.2.1. Việt hóa Humanres
Như đã thấy ở trên, ngôn ngữ mặc định cho người dùng OFBiz là Tiếng anh, điều đó một phần gây khó khăn cho những nhà quản trị nhân sự. Bước tiếp theo chúng ta sẽ nghiên cứu việc Việt hóa hệ quản trị nhân sự Humanres trong OFBiz.
Vì OFBiz là hệ mã nguồn mở nên hỗ trợ rất nhiều ngôn ngữ, tiêu biểu trong đó là tiếng Anh, Pháp, Italy, Nga, Trung quốc .. Mỗi ngôn ngữ sẽ có một mã riêng tương ứng như hình vẽ dưới đây. Mã cho Tiếng Việt là [vi].
42
Để có thể Việt hóa hệ quản trị Humanres của OFBiz ta cần phải hiểu vị trí đặt các file ngôn ngữ trong OFBiz. Trong trường hợp này, ngôn ngữ được khai báo trong các file XML UILabels đặt trong thư mục config của framework và các ứng dụng. Với các file UILabels đặt trong {ofbiz}/humanres/config sẽ quy định ngôn ngữ cho riêng hệ quản trị Humanres và các file XML UILabels đặt trong {ofbiz}/…/config quy định ngôn ngữ chung của toàn hệ quản trị OFBiz.
Như cấu trúc bên dưới đây chúng ta có thể thấy một ví dụ về việc khai báo các trường và ngôn ngữ được dùng cho trường đó.
- <property key=””></property> : Dùng để khai báo trường trong OFBiz
43
Để Việt hóa chúng ta thêm giá trị <value xml:lang=”vi”></value> vào khai báo của mỗi trường. Làm tương tự với từng thành phần trong file xml HumanUILables ta sẽ Việt hóa được HR trong OFBiz.
Sau khi hoàn thành, chúng ta chạy lại OFBiz để hệ thống load lại dữ liệu được cập nhật. Tiếp theo tìm đến phần lựa chọn ngôn ngữ và đổi sang sử dụng Tiếng Việt, chúng ta có thể có được giao diện sử dụng như hình vẽ :
4.2.2. Thêm module mới
<property key="FormFieldTitle_applyingPartyId">
<value xml:lang="de">Anwendungsteilnehmer ID</value> <value xml:lang="en">Applying Party Id</value>
<value xml:lang="fr">Réf. d'acteur en demande</value> <value xml:lang="it">Soggetto Applicato</value> <value xml:lang="th">รหัสกลุ่มผู้ใช้</value>
<value xml:lang="zh">应聘申请人</value>
<value xml:lang="vi">ID phòng tuyển dụng</value>// Việt hóa
</property>
<property key="FormFieldTitle_bankName"> <value xml:lang="en">Bank Name</value>
<value xml:lang="fr">Nom de la banque</value> <value xml:lang="it">Nome Banca</value> <value xml:lang="th">ชื่อธนาคาร</value> <value xml:lang="zh">银行名称</value>
44
Hiện tại ứng dụng HR trong OFBiz có đầy đủ chức năng cần thiết để quản trị nhân sự trong một công ty nên không cần thiết phải thêm bất kì module mới nào. Dưới đây em sẽ trình bày cách thức viết một module mẫu trong OFBiz.
4.2.2.1. Xác định mô hình dữ liệu
Bước đầu tiên là xác định mô hình dữ liệu. Chúng ta muốn theo dõi từng cá nhân, sở thích của họ và tra cứu tất cả các sở thích của từng cá nhân ( hoặc tất cả mọi người có cùng 1 sở thích ). Do đó, mô hình dữ liệu ứng dụng với mỗi cá nhân, sở thích và liên kết giữa mỗi cá nhân và sở thích.
Với một cơ sở dữ liệu quan hệ, chúng ta sẽ định nghĩa hai bảng, một cho người và một cho một sở thích và liên kết chúng với nhau qua một bảng thứ ba. Bảng thứ ba sẽ cho phép bạn kết hợp bấy nhiêu sở thích mà bạn mong muốn với một người và ngược lại. Bạn sẽ định nghĩa khóa ngoài(foreign key) để ràng buộc bảng thứ ba chỉ dung để chỉ người và sở thích đang có.
OFBiz cũng hoạt động tương tự. Chúng ta sẽ xác định hai thực thể, trong đó chúng ta sẽ gọi là HelloPerson và HelloHobby, và xây dựng một liên kết
HelloPersonHobby, sau đó thiết lập mối quan hệ giữa chúng. Mối quan hệ này được sử dụng như một ràng buộc khóa ngoài nhưng cũng cho phép chúng ta đi từ một thực thể đến một thực thể khác mà không phải tự mình nhớ từng khóa của chúng là gì (hoặc thay đổi code khi khóa thay đổi).
<entity entity-name="HelloPerson" package-name="org.ofbiz.hello3"
title="Entity for storing data about persons"> <field name="helloPersonId" type="id-ne"></field> <field name="firstName" type="id"></field>
<field name="lastName" type="id"></field> <field name="comments" type="comment"> </field> <prim-key field="helloPersonId"/>
</entity>
<entity entity-name="HelloHobby"
package-name="org.ofbiz.hello3" title="Hobbies avaiable">
<field name="helloHobbyId" type="id-ne"></field> <field name="description" type="description"></field> <prim-key field="helloHobbyId"/>
</entity>
<entity entity-name="HelloPersonHobby"
package-name="org.ofbiz.hello3" title="Entity and atribute Entity">
<field name="helloPersonId" type="id-ne"></field> <field name="helloHobbyId" type="id-ne"></field> <prim-key field="helloPersonId"/>
<prim-key field="helloHobbyId"/>
<relation type="one" fk-name="HPRSN_PRSN" rel-entity- name="HelloPerson">
<key-map field-name="helloPersonId"/> </relation>
<relation type="one" fk-name="HPRSN_HBBY" rel-entity- name="HelloHobby">
<key-map field-name="helloHobbyId"/> </relation>
45
Chú ý : Ở đây, chúng ta đang tạo ra một ứng dụng với mô hình dữ liệu hoàn toàn khép kín để minh họa. Nếu chúng ta xây dựng một ứng dụng thực tế, việc thực hành tốt nhất nếu chúng ta dùng lại được nhiều thực thể trong OFBiz nhất có thể, nên thay vì tạo ra HelloPerson riêng, chúng ta sẽ sử dụng các thực thể Party/ Person / PartGroup tồn tại của OFBiz.
Để xác định mô hình dữ liệu, tạo ra một thư mục bên trong Aplication ( trong trường hợp này là hello3 ) và tạo ra một file entitymodel.xml và entitygroup.xmld trong thư mục entitydef.
HelloPerson và HelloHobby là 2 khóa chính, và HelloPersonHobby có 2 khóa chính, trong đó nó sử dụng liên kết HelloPerson và HelloHobby. Nó được xem là sự áp dụng tốt để cung cấp một tên khóa ngoài cho các quan hệ, để giúp việc gỡ lỗi dễ dàng hơn và tránh trùng tên giữa các khóa ngoài do bạn tạo ra trong OFBiz.
Điều đó cũng rất quan trọng ( nhưng rất dễ quên ) để xác định các thực thể đó trong một file khác, entitygroup.xml, trong thư mục, do đó OFBiz sẽ biết được đâu là khóa đại diện và như vậy cơ sở dữ liệu sẽ được sử dụng.
Nếu không, các thực thể sẽ vẫn tồn tại trong OFBiz nhưng khi chúng ta thực sự cố gắng sử dụng chúng , chúng ta sẽ nhận được lỗi như sau :
org.ofbiz.entity.GenericEntityException: Helper name not found for entity HelloPerson
Cuối cùng, chúng ta phải thêm dòng dưới đây vào ofbiz-component.xml để OFBiz có thể biết sử dụng thực thể này như một phần ứng dụng của mình, phía trước <webapp>
Bây giờ chúng ta sẽ khởi động OFBiz, chúng ta sẽ thấy những thông báo trong consolo.log (Linux) hoặc giao diện điều khiển (Windows) , thông báo với bạn rằng thực thể của bạn đã được nạp :
<entity-resource type="model" reader-name="main" loader="main" location="entitydef/entitymodel.xml"/>
<entity-resource type="group" reader-name="main" loader="main" location="entitydef/entitygroup.xml"/>
5336 (main) [ UtilXml.java:242:DEBUG] XML Read 0.0070s: /home/sichen/eclipse/workspace/ofbiz/hot-
deploy/hello3/entitydef/entitymodel.xml
5693 (main) [ UtilXml.java:242:DEBUG] XML Read 0.0050s: /home/sichen/eclipse/workspace/ofbiz/hot-
46
Khi đó bạn vào webtools, bạn có thể thấy những thực thể :
Click vào “All” bên phải HelloPerson bạn sẽ thấy tất cả những trường của mình :
47
Chú ý rằng bên cạnh mỗi trường là kiểu Java và kiểu SQL cho từng trường. Loại SQL được quy định trong framework/entity/filedtype/ thư mục và thay đổi tùy theo cơ sở dữ liệu bạn đang sử dụng (đang dùng trên là Derby). Nếu có bất kỳ già trị nào cho thực thể này, nó sẽ được hiển thị bên dưới các trường.
4.2.2.2. Tạo dữ liệu gốc
Tiếp theo chúng ta sẽ tạo ra một số dữ liệu gốc cho sở thích của chúng ta. Trong hầu hết các ứng dụng của OFBiz, chúng ta sẽ tạo ra thư mục data trong ứng dụng và tạo file XML cho dữ liệu gốc. Chúng ta đặt tên file đó là HobbiesData.xml:
File này được gọi là file phương tiện thực thể (entity engine)dạng file XML, là một định dạng tiêu chuẩn của OFBiz dùng cho việc nhập và xuất dữ liệu. Nó thực sự rất đơn giản. Sử dụng tên của thực thể ( “HelloHobby” trong trường hợp của chúng ta ) cho thẻ tên, và sử dụng tên các trường hoặc thuộc tính như bên trong các thẻ (Xem giá trị cuối cùng cho “WINE”. Các giá trị cho các trường của chúng ta có thẻ là giá trị của các thuộc tính hoặc bên trong các thẻ nội bộ(inner tags), cũng như nơi chúng có thể ở bên trong CDATA, trong trường hợp bạn có giá trị rất dài. Ngoài ra các khóa cho từng trường không cần phải là chữ hoa hoặc cách nhau bởi dấu _ , nhưng đó là quy tắc tiêu chuẩn của ứng dụng OFBiz).
Bây giờ, chúng ta đã sẵn sàng để nạp dữ liệu gốc. Chuyển tới màn hình chính của ứng dụng Webtools, và chúng ta sẽ thấy liên kết “XML Import”. Nhấn
<?xml version="1.0" encoding="UTF-8"?> <entity-engine-xml>
<HelloHobby helloHobbyId="READING" description="Reading"/> <HelloHobby helloHobbyId="MOVIES" description="Movies"/> <HelloHobby helloHobbyId="THEATER" description="The theater"/> <HelloHobby helloHobbyId="OPERA" description="The Opera"/> <HelloHobby helloHobbyId="SKIING" description="Skiing"/> <HelloHobby helloHobbyId="SURFING" description="Surfing"/>
<HelloHobby helloHobbyId="WINDSURFING" description="Windsurfing"/> <HelloHobby helloHobbyId="BASKETBALL" description="Basketball"/> <HelloHobby helloHobbyId="FOOLBALL" description="Football"/> <HelloHobby helloHobbyId="FOOTBALL_US" description="Soccer"/> <HelloHobby helloHobbyId="COOKING" description="Cooking"/> <HelloHobby helloHobbyId="WINE">
<description >Wine </description> </HelloHobby>
48
vào nút “XML Import” và trên màn hình kế tiếp sẽ yêu cầu điền tên của tập tin của chúng ta, liên quan đến thư mục OFBiz. Tôi thường không bấm vào bất kỳ hộp kiểm tra tùy chọn nào và chỉ cần nhập “Import”. Nếu chúng ta thành công, sẽ có một màn hình tương tự trở lại và hiển thị ở dưới báo cho bạn biết có bao nhiêu giá trị được thêm vào :
Nếu quá trình import dữ liệu bị hỏng, chúng ta nên đọc các thông báo lỗi từ console.log cẩn thận. Thường là do những lý do sau đây :
1. Sử dụng giá trị quá dài cho primary key. Các ID trong OFBiz thường là biến kiểu String trong Java, nhưng đối với SQL nó là kiểu 20-char VARCHAR.
2. Thiếu một khóa chính cần thiết.
49
Nếu chúng ta đọc cẩn thận file .log, chúng ta có thể xác định được giá trị OFBiz nào đã được tạo ra và phản ứng về dữ liệu lỗi từ hệ thống là gì. Nó cũng có thể đưa cho chúng ta một cái tên khóa ngoài hơi khó hiểu để tìm ra sự vi phạm điều kiện của khóa ngoài.
Chúng ta cũng có thể nhận thấy một đường dẫn thông báo “XML Export” trên trang Webtools. Các liên kết này có thể tạo ra các thực thể XML file.
Tiếp theo, chúng ta xem phần “Entity Maintenance”. Từ trang “Main”, click vào “All” bên cạnh HelloHobby, chúng ta sẽ thấy những sở thích đã được chèn vào :