?三層工程結(jié)構(gòu)
項(xiàng)目里采用的工程結(jié)構(gòu)是官方推薦的“三層工程結(jié)構(gòu)”伐蒂,本質(zhì)上和Android工程里的結(jié)構(gòu)是類似的煞躬。如下圖HMOSWorld里的工程結(jié)構(gòu):
1、common(公共能力層):
該路徑下的各個(gè)module是一些公共基礎(chǔ)能力逸邦,比如工具庫(kù)恩沛、公共配置、通用常量缕减、自定義基礎(chǔ)組件等雷客。
common路徑下的各個(gè)module可以根據(jù)具體的module設(shè)計(jì)需求,在創(chuàng)建時(shí)可以選擇Shared Library或Static Library烛卧,選擇了Static Library創(chuàng)建的后續(xù)需編譯成一個(gè)HAR包佛纫。該路徑下的module們只可以被products或features路徑下的module依賴,不可以反向依賴总放。該路徑下的module之間是可以橫向調(diào)用的呈宇。
注意:a、選擇Shared Library創(chuàng)建的module局雄,在后續(xù)編譯時(shí)甥啄,會(huì)生成一個(gè).hsp文件,同時(shí)其內(nèi)部的使用export關(guān)鍵字修飾的class炬搭、interface蜈漓、function等可導(dǎo)出項(xiàng)還會(huì)被組合一起打一個(gè).har包宫盔。各個(gè)宿主module通過該.har來引用HSP里的導(dǎo)出項(xiàng)有额,但是在進(jìn)程中該HSP的代碼只有一份,大家共享茴迁。
b、選擇Static Library創(chuàng)建的module倦卖,在后續(xù)編譯時(shí)糖耸,該module會(huì)被打成一個(gè)har包嘉竟,凡是引用了該module里的可導(dǎo)出項(xiàng)或資源的宿主module舍扰,在后續(xù)打出的hap包里都會(huì)擁有該har包希坚。要注意避免引入過多的無用代碼裁僧。
2、features(基礎(chǔ)特性層/業(yè)務(wù)模塊層):
該路徑下一般是各個(gè)業(yè)務(wù)模塊茬底,各個(gè)module高內(nèi)聚获洲、低耦合贡珊,可以供products層的各個(gè)entry選擇性地引用门岔,以實(shí)現(xiàn)靈活地部署寒随。不需要單獨(dú)部署的module通常會(huì)被編譯為HAR包逢防,供products層或features層的其它module使用忘朝。需要單獨(dú)部署的module通常會(huì)被編譯為Feature類型的HAP包,和products下Entry類型的HAP包進(jìn)行組合部署晦墙。features層里的各個(gè)module可以橫向調(diào)用及依賴common層晌畅,同時(shí)可以被products層里的不同設(shè)備形態(tài)的HAP(可以認(rèn)為是不同的項(xiàng)目)所依賴但指,但是不能反向依賴products層里的entry module抗楔。
在創(chuàng)建時(shí),選擇前面圖中的Empty Ability连躏,選擇feature。
3入热、products(產(chǎn)品定制層):
該路徑下的各個(gè)entry module是在不同的設(shè)備情況下app應(yīng)用的入口拍棕,每個(gè)module會(huì)針對(duì)不同的設(shè)備形態(tài)進(jìn)行不同的功能和特性集成。
它們各自被編譯為一個(gè)Entry類型的HAP包绰播,作為應(yīng)用主入口。products層不可以橫向調(diào)用。
注意:整個(gè)代碼工程最終會(huì)構(gòu)建出一個(gè)APP包尾组,應(yīng)用以APP包的形式發(fā)布到應(yīng)用市場(chǎng)中。
引用module
在工程內(nèi)上層引用下層的module時(shí)
有兩種簡(jiǎn)單的操作方式:
a跨跨、在Terminal窗口中囱皿,執(zhí)行如下命令進(jìn)行安裝嘱腥,IDE會(huì)在引用方module里的oh-package.json5中自動(dòng)添加依賴。
比如entry要引用不同路徑下的utils拘悦,utils要引用同路徑下的constants:
cd entry 或 cd ../common/utils//? 切到entry module目錄下 或 切到common路徑下的utils module目錄下
ohpm install ../common/utils 或 ohpm install ../constants// 把utils module引用到entry module中 或 把同為common路徑下的constants module引用到utils module中
結(jié)果如下齿兔,在oh-package.json5文件中的dependencies里會(huì)生成依賴項(xiàng):
{
? "name": "entry",
? "version": "1.0.0",
? "description": "Please describe the basic information.",
? "main": "",
? "author": "",
? "license": "",
? "dependencies": {
? ? "@ohos/utils": "file:../common/utils"? ? ? ? ? // key為utils module的name,value是utils module的路徑
? },
? "devDependencies": {},
? "dynamicDependencies": {}
}
// 或者
{
? "name": "@ohos/utils",
? "version": "1.0.0",
? "description": "Please describe the basic information.",
? "main": "Index.ets",
? "author": "",
? "license": "Apache-2.0",
? "dependencies": {
? ? "constants": "file:../constants"? ? ? ? ? ? // key為同路徑下的constants module的name础米,value是constants module的路徑
? },
? "devDependencies": {},
? "dynamicDependencies": {}
}
b分苇、直接在entry或utils下的oh-package.json5文件中手動(dòng)添加依賴項(xiàng),然后sync project屁桑。
引用社區(qū)庫(kù)時(shí)
社區(qū)庫(kù)是指由代碼貢獻(xiàn)者已經(jīng)上架到ohpm中心供其他開發(fā)者下載使用的庫(kù)医寿,可以通過如下兩種方式設(shè)置對(duì)ohpm倉(cāng)三方包的依賴信息,這里推薦第一種蘑斧。
(下面步驟以@ohos/lottie三方庫(kù)舉例):
方式一:在Terminal窗口中靖秩,執(zhí)行如下命令安裝三方包,DevEco Studio會(huì)自動(dòng)在當(dāng)前module中的oh-package.json5中自動(dòng)添加三方包依賴乌叶。
ohpm install @ohos/lottie
結(jié)果示例:
{
? "name": "entry",
? "version": "1.0.0",
? "description": "Please describe the basic information.",
? "main": "",
? "author": "",
? "license": "",
? "dependencies": {
? ? "@ohos/utils": "file:../common/utils",
? ? "@ohos/lottie": "^2.0.12"? ? ? ? // 注意:value里版本號(hào)前面有個(gè)符合^
? },
? "devDependencies": {},
? "dynamicDependencies": {}
}
方式二:在工程的某個(gè)module中的oh-package.json5文件中設(shè)置三方包依賴盆偿,配置示例如下:
"dependencies": {
? "@ohos/lottie": "^2.0.12"
}
其實(shí)是跟上面的步驟一樣的,只是手動(dòng)處理下而已准浴。
module的name里包含@ohos
在一個(gè)module里的oh-package.json5文件中事扭,name字段對(duì)應(yīng)的字符串值是用于設(shè)置該module的名稱的。如果名稱中包含了@ohos/這樣的字樣乐横,表明這是一個(gè)屬于鴻蒙操作系統(tǒng)生態(tài)里(ohpm倉(cāng)庫(kù))提供的可供三方應(yīng)用使用的庫(kù)求橄。‘@ohos’命名標(biāo)識(shí)是用于區(qū)分是社區(qū)庫(kù)提供的模塊還是用戶工程里自定義的其他模塊葡公。
例如罐农,我們想要引用一個(gè)社區(qū)庫(kù)時(shí),如網(wǎng)絡(luò)模塊axios催什。在提供方工程的axios module里涵亏,它的oh-package.json5中的name應(yīng)該這樣寫:
{
? ? "name": "@ohos/axios",
? ? "description": "Axios ,是一個(gè)基于 promise 的網(wǎng)絡(luò)請(qǐng)求庫(kù)蒲凶。本庫(kù)气筋。。旋圆。",
? ? // ....
}
在我們的代碼中就可以通過@ohos/axios來引用這個(gè)模塊了宠默,這有助于避免與我們自己工程里的同名模塊發(fā)生沖突,我們工程里引用axios模塊的module里的oh-package.json5文件如下:
{
? "name": "entry",
? // ...
? "dependencies": {
? ? "constants": "file:../constants",? ? ? // 自己工程里的constants module
? ? "@ohos/axios": "^2.2.3"? ? ? ? ? ? ? ? // 發(fā)布到ohos社區(qū)庫(kù)里的開源庫(kù)axios
? }
}
應(yīng)用程序包的結(jié)構(gòu)
工程里的多module機(jī)制
在進(jìn)行應(yīng)用開發(fā)時(shí)灵巧,一個(gè)應(yīng)用工程中通常包含一個(gè)或多個(gè)Module搀矫。Module中包含了源代碼抹沪、資源文件、第三方庫(kù)及應(yīng)用/服務(wù)配置文件瓤球,每一個(gè)Module都可以獨(dú)立進(jìn)行編譯和運(yùn)行融欧。
Module分為“Ability”和“Library”兩種類型:
“Ability”類型的Module編譯后生成HAP包,type為entry或feature冰垄。
“Library”類型的Module編譯后生成HAR包蹬癌,type為har或shared,shared的同時(shí)還生成hsp包虹茶。
不同類型的hap包
HarmonyOS應(yīng)用是以APP Pack的形式發(fā)布的,app包里包含了一個(gè)或多個(gè)hap包隅要。HAP是HarmonyOS應(yīng)用在安裝時(shí)的基本單位蝴罪,HAP可以分為Entry和Feature兩種類型:
1、Entry類型的HAP:即應(yīng)用的主模塊步清。在同一個(gè)應(yīng)用中要门,同一設(shè)備類型只支持一個(gè)Entry類型的HAP,通常用于實(shí)現(xiàn)應(yīng)用的入口界面廓啊、入口圖標(biāo)欢搜、主特性功能等。
注意:不同的設(shè)備形態(tài)谴轮,比如手機(jī)(phone)和平板(tablet)屬于不同的形態(tài)炒瘟,是分別有不同的Entry類型的hap包的,但是它們都在同一個(gè)app pack中第步,應(yīng)用是以pack上架應(yīng)用市場(chǎng)的疮装,在不同的設(shè)備形態(tài)上的應(yīng)用市場(chǎng)中可以分別下載安裝各自對(duì)應(yīng)的Entry類型的hap包。
2粘都、Feature類型的HAP:應(yīng)用的動(dòng)態(tài)特性模塊廓推。Feature類型的HAP通常用于實(shí)現(xiàn)應(yīng)用的特性功能,一個(gè)應(yīng)用程序包可以包含一個(gè)或多個(gè)Feature類型的HAP翩隧,也可以不包含樊展。
編譯態(tài)的包結(jié)構(gòu)
不同類型的Module編譯后會(huì)生成對(duì)應(yīng)的HAP、HAR堆生、HSP等文件专缠,開發(fā)態(tài)視圖與編譯態(tài)視圖的對(duì)照關(guān)系如下:
從開發(fā)態(tài)到編譯態(tài),一個(gè)Module中的文件會(huì)發(fā)生如下變更:
ets目錄:里面的所有ArkTS源碼會(huì)被編譯生成一個(gè).abc文件顽频。
resources目錄:AppScope目錄下的資源文件會(huì)合入到每個(gè)Module下面的資源目錄中藤肢,如果兩個(gè)目錄下存在重名文件,編譯打包后只會(huì)保留AppScope目錄下的資源文件糯景。
module配置文件:AppScope目錄下的app.json5文件字段會(huì)合入到每個(gè)Module下面的module.json5文件之中嘁圈,編譯后生成HAP或HSP最終的module.json文件省骂。
注意:在編譯生成HAP和HSP時(shí),會(huì)把他們所依賴的HAR包直接編譯到HAP和HSP中最住。
發(fā)布態(tài)的包結(jié)構(gòu)
每個(gè)應(yīng)用(app pack)中至少包含了一個(gè).hap文件钞澳,同時(shí)可能包含若干個(gè).hsp文件,也可能不含涨缚。一個(gè)應(yīng)用中的所有的.hap與.hsp文件合在一起稱為Bundle轧粟,它的bundleName字段的值是應(yīng)用的唯一標(biāo)識(shí),即安卓中常說的包名脓魏。
當(dāng)一個(gè)應(yīng)用要發(fā)布上架到應(yīng)用市場(chǎng)時(shí)兰吟,需要將Bundle打包為一個(gè).app后綴的文件用于上架,這個(gè).app文件稱為App Pack(Application Package)茂翔,與此同時(shí)混蔼,DevEco Studio工具會(huì)自動(dòng)生成一個(gè)pack.info文件。pack.info文件里描述了App Pack中每個(gè)HAP和HSP的屬性珊燎,包含APP中的bundleName和versionCode信息惭嚣、以及每個(gè)Module中的name、type和abilities等信息悔政。
所以晚吞,發(fā)布態(tài)的包結(jié)構(gòu)里包含了:1個(gè)entry.hap、0個(gè)或多個(gè)feature.hap谋国、0個(gè)或多個(gè)library.hsp槽地、pack.info峭咒。
打包-上架-下載安裝的流程如下:
注意:
1婆芦、App Pack是發(fā)布上架到應(yīng)用市場(chǎng)的基本單元,但是不能在設(shè)備上直接安裝和運(yùn)行能真。
2旅急、在應(yīng)用簽名逢勾、云端分發(fā)、端側(cè)安裝時(shí)藐吮,都是以HAP/HSP為單位進(jìn)行簽名溺拱、分發(fā)和安裝的。
結(jié)語:希望每一次梳理-總結(jié)都能帶給你我一定的收獲谣辞。迫摔。。