自我進(jìn)入到代碼這個(gè)行業(yè)開(kāi)始箍铲,就有前輩早早告訴我要積極活躍在開(kāi)源社區(qū)冻押,于是認(rèn)識(shí)了 github, 然后也見(jiàn)識(shí)到了開(kāi)源社區(qū)的魅力之處×墼桑看到大神們都會(huì)積極貢獻(xiàn)自己的開(kāi)源倉(cāng)庫(kù)昨寞,自己也被這種開(kāi)源精神感動(dòng)到了。過(guò)程中我也嘗試寫(xiě)過(guò)一些小框架厦滤,但是發(fā)布到 jcenter 上援岩,所以知名度大大降低。
相比于幾年前掏导,現(xiàn)在直接拷貝源代碼到自己工程中的做法越來(lái)越少了享怀。得益于 Android 使用 Gradle 管理依賴(lài),更多的人選擇將開(kāi)源倉(cāng)庫(kù)發(fā)布到 jcenter 中趟咆,然后被更多的人使用添瓷。今天我們將嘗試從零開(kāi)始,一步步上傳自己的應(yīng)用到 Jcenter值纱,然后優(yōu)雅的通過(guò) gradle compile 'x.y.z:a:0.0.1'
引用鳞贷。
理解 Android Gradle 構(gòu)建
以 BottomTabAndroid 工程為例,在一個(gè)項(xiàng)目中通常至少有三個(gè) gradle 文件虐唠,分別為:
- BottomTabAndroid/settings.gradle
- BottomTabAndroid/build.gradle
- BottomTabAndroid/app/build.gradle
分析各 gradle 文件的具體內(nèi)容搀愧,我們可以發(fā)現(xiàn)位于最外層的 settings.gradle 定義項(xiàng)目中的各個(gè)不同 module,這時(shí)候指定的 module 才能被我們的工程識(shí)別疆偿。識(shí)別之后咱筛,如果 A module 需要引用 B module,那么在 A 的 build.gradle 文件中杆故,則需要 compile project(':B')
迅箩。
在這個(gè)工程中,存在 bottomtab 和 app 兩個(gè) module, 而 bottomtab 被 app 所引用处铛。
settings.gradle 內(nèi)容如下:
include ':app', ':bottomtab'
build.gradle 內(nèi)容如下:
buildscript {
repositories {
// 指定構(gòu)建腳本的下載庫(kù)
jcenter()
}
dependencies {
// 指定引入何種構(gòu)建腳本沙热,比如注釋中引入了上傳到 jecneter 和 maven 構(gòu)建的腳本
classpath 'com.android.tools.build:gradle:2.2.3'
// classpath 'com.jfrog.bintray.gradle:gradle-bintray-plugin:1.7.3'
// classpath 'com.github.dcendents:android-maven-gradle-plugin:1.5'
}
}
allprojects {
repositories {
// 指定從何處下載子項(xiàng)目的庫(kù)依賴(lài)
jcenter()
// maven {
// url 'https://dl.bintray.com/gongmingqm10/maven/'
// }
}
}
task clean(type: Delete) {
delete rootProject.buildDir
}
build.gradle 文件中主要定義了 buildscript和 allprojects.repositories 兩部分內(nèi)容叉钥。確定了當(dāng)前項(xiàng)目中使用的構(gòu)建腳本庫(kù),以及項(xiàng)目中依賴(lài)庫(kù)的下載倉(cāng)庫(kù)篙贸。
app/build.gradle 文件則定義了當(dāng)前 module 的配置信息投队,比如 Android 工程中需要對(duì) API,簽名爵川,項(xiàng)目依賴(lài)等信息進(jìn)行配置敷鸦。本文暫且略過(guò)其詳細(xì)介紹。
認(rèn)識(shí)了 Gradle 的基本配置寝贡,我們?cè)倏纯慈缦逻@句熟悉的 Gradle 語(yǔ)言:
compile 'net.gongmingqm10.uikit:bottomtab:0.2.0'
所有的倉(cāng)庫(kù)都是按照 Group_ID:ARTIFACT_ID:VERSION
定義扒披,所以對(duì)于 bottomtab 這個(gè)庫(kù)而言, groupID = net.gongmingqm10.uikit圃泡, artifactId = bottomtab碟案,version = 0.2.0。這種方式的好處是颇蜡,我不需要在項(xiàng)目中導(dǎo)入眾多的子 module价说,只需要通過(guò)這一句 DSL (領(lǐng)域特定語(yǔ)言) 引入倉(cāng)庫(kù),并且能夠隨時(shí)更改版本风秤。
下面我們一步步構(gòu)建出這個(gè) net.gongmingqm10.uikit.bottomtab
依賴(lài)庫(kù)鳖目,上傳到 jcenter,以在項(xiàng)目中直接使用缤弦。
發(fā)布開(kāi)源庫(kù)
本階段我們將從零開(kāi)始一步步構(gòu)建并發(fā)布自己的第一款開(kāi)源庫(kù)领迈。我們假設(shè)你已經(jīng)在使用 Android Studio 開(kāi)發(fā)應(yīng)用,并且對(duì) Gradle 有一定的了解碍沐。Android 倉(cāng)庫(kù)通常有兩種格式狸捅,aar 和 jar,其中 aar 格式中包含 Android 自身相關(guān)的資源文件累提。而 jar 則主要包含 .class 類(lèi)文件尘喝。考慮到我們希望做出一款 Bottom Tab 底部欄的庫(kù)刻恭,因此我們最后使用的是 aar 格式。
1. 配置 bintray
首先注冊(cè) Bintray OpenSource扯夭,如果之前有賬號(hào)請(qǐng)?zhí)^(guò)此步驟鳍贾。通過(guò) OpenSource 途徑注冊(cè)的 bintray 屬于公開(kāi)免費(fèi)版,這正和我的期望相符交洗。注意不要直接在首頁(yè)注冊(cè)骑科,那樣默認(rèn)注冊(cè)的是收費(fèi)版本。
訪(fǎng)問(wèn)個(gè)人主頁(yè)构拳,點(diǎn)擊 "Add New Repository" 跳轉(zhuǎn)到創(chuàng)建 repository 頁(yè)面咆爽,這里我們需要?jiǎng)?chuàng)建一個(gè) name = maven梁棠,type = Maven 的 Repository。其中的 license 以及 description 按照個(gè)人偏好自行填寫(xiě)斗埂。
點(diǎn)擊 Create
之后符糊,我們可以順利在首頁(yè)看到 repository 中多了一個(gè) maven 的倉(cāng)庫(kù)。
點(diǎn)擊剛創(chuàng)建的 maven 倉(cāng)庫(kù)呛凶,如果是第一次創(chuàng)建男娄,應(yīng)該看不到任何的 package。我們需要 Add New Package
漾稀。
創(chuàng)建 package 時(shí)模闲,我們填寫(xiě) packageName = ‘bottom-tab’,這個(gè)屬性比較重要崭捍,在后續(xù)步驟的 gradle 中需要用到尸折。注意到需要填寫(xiě) versionControl,我提前在 github 上創(chuàng)建了一個(gè) repository bottomtab殷蛇,然后把URL填入即可实夹。
創(chuàng)建完成之后,bintray 的配置基本告一段落晾咪。但是正式開(kāi)始之前我們還需要拿到 API_KEY收擦,要不然所有人都可以更新你的庫(kù),豈不是一件很恐怖的事情谍倦。
總結(jié)這一步塞赂,我們所需要完成的事情:
- 注冊(cè)bintray,獲得 bintray 用戶(hù)名和 API KEY;
- 在 GITHUB 新建 bottom-tab 倉(cāng)庫(kù)昼蛀;
- 在 bintray 新建 maven/bottom-tab 倉(cāng)庫(kù)宴猾;
2. 配置 GRADLE 工程
為了發(fā)布一款 “接地氣” 的 bottom-tab 庫(kù),我們先構(gòu)建一個(gè) BottomTabAndroid 應(yīng)用叼旋,然后添加 bottom-tab 子模塊仇哆,然后將 bottom-tab 子模塊打包并發(fā)布到 jcenter 上,而 app 模塊則是一個(gè) demo夫植。展示 bottom-tab 的實(shí)際效果讹剔。
具體代碼請(qǐng)參考:https://github.com/gongmingqm10/BottomTabAndroid。項(xiàng)目截圖如下:
開(kāi)發(fā)過(guò)程中详民,我先讓 app 直接引用子模塊 bottom-tab延欠,功能開(kāi)發(fā)完成之后,開(kāi)始準(zhǔn)備最重要的打包上傳沈跨。
Step 1: 配置 local.properties
我們需要將 bintray 賬戶(hù)相關(guān)的 username 和 apikey 存放在此文件中由捎。在提交代碼時(shí),此文件被自動(dòng)忽略饿凛,從而保證了其安全性狞玛。默認(rèn)的 local.properties 文件中保存了 sdk 路徑软驰。我們?cè)谄浜筇砑由?uername 和 apikey:
sdk.dir=/Users/mingong/Project/sdk
bintray.user=gongmingqm10
bintray.apikey=thisissomesecretkeyanddonotcopyme
請(qǐng)將你自己的 username 和 apikey 復(fù)制替換到此文件。
Step 2: 配置 $projectDir/build.gradle
為了上傳 bintray心肪,我們需要使用 gradle-bintray-plugin 和 android-maven-gradle-plugin 兩款構(gòu)建插件锭亏。
buildscript {
repositories {
jcenter()
}
dependencies {
classpath 'com.android.tools.build:gradle:2.2.3'
// 添加如下插件以上傳 AAR 至 bintray
classpath 'com.jfrog.bintray.gradle:gradle-bintray-plugin:1.7.3'
classpath 'com.github.dcendents:android-maven-gradle-plugin:1.5'
}
}
...
請(qǐng)關(guān)注 buildscript{dependecies{}} 中配置,其余的配置項(xiàng)已省略蒙畴。
Step 3: 配置 $projectDir/bottomtab/build.gradle
apply plugin: 'com.android.library'
apply plugin: 'com.github.dcendents.android-maven'
apply plugin: 'com.jfrog.bintray'
android {
compileSdkVersion 23
buildToolsVersion "23.0.3"
defaultConfig {
minSdkVersion 17
targetSdkVersion 23
versionCode 1
versionName "1.0"
testInstrumentationRunner "android.support.test.runner.AndroidJUnitRunner"
}
buildTypes {
release {
minifyEnabled false
proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'
}
}
}
dependencies {
compile fileTree(dir: 'libs', include: ['*.jar'])
androidTestCompile('com.android.support.test.espresso:espresso-core:2.2.2', {
exclude group: 'com.android.support', module: 'support-annotations'
})
compile 'com.android.support:appcompat-v7:23.3.0'
testCompile 'junit:junit:4.12'
}
if (project.hasProperty("android")) { // Android libraries
task sourcesJar(type: Jar) {
classifier = 'sources'
from android.sourceSets.main.java.srcDirs
}
task javadoc(type: Javadoc) {
source = android.sourceSets.main.java.srcDirs
classpath += project.files(android.getBootClasspath().join(File.pathSeparator))
}
} else { // Java libraries
task sourcesJar(type: Jar, dependsOn: classes) {
classifier = 'sources'
from sourceSets.main.allSource
}
}
task javadocJar(type: Jar, dependsOn: javadoc) {
classifier = 'javadoc'
from javadoc.destinationDir
}
artifacts {
archives javadocJar
archives sourcesJar
}
// 你只需要把這里的參數(shù)修改為自己的庫(kù)名稱(chēng)即可
ext {
siteUrl = 'https://github.com/gongmingqm10/BottomTabAndroid'
gitUrl = 'https://github.com/gongmingqm10/BottomTabAndroid.git'
currentVersion = '0.2.0'
groupId = 'net.gongmingqm10.uikit'
artifactId = 'bottom-tab'
desc = 'Android bottom tab'
}
group = groupId
version = currentVersion
install {
repositories.mavenInstaller {
pom {
project {
name artifactId
description desc
url siteUrl
packaging 'aar'
groupId groupId
artifactId artifactId
version currentVersion
licenses {
license {
name 'The Apache Software License, Version 2.0'
url 'http://www.apache.org/licenses/LICENSE-2.0.txt'
}
}
developers {
developer {
id 'gongmingqm10'
name 'Ming Gong'
email 'gongmingqm10@foxmail.com'
}
}
scm {
connection gitUrl
developerConnection gitUrl
url siteUrl
}
}
}
}
}
Properties properties = new Properties()
properties.load(project.rootProject.file('local.properties').newDataInputStream())
bintray {
user = properties.getProperty("bintray.user")
key = properties.getProperty("bintray.apikey")
configurations = ['archives']
pkg {
repo = "maven"
name = artifactId
websiteUrl = siteUrl
vcsUrl = gitUrl
licenses = ["Apache-2.0"]
publish = true
publicDownloadNumbers = true
}
}
注意贰镣,其中大部分配置都是很通用的,對(duì)于不同的 library膳凝,我們只需要修改如下不同的配置即可:
// 你只需要把這里的參數(shù)修改為自己的庫(kù)名稱(chēng)即可
ext {
siteUrl = 'https://github.com/gongmingqm10/BottomTabAndroid'
gitUrl = 'https://github.com/gongmingqm10/BottomTabAndroid.git'
currentVersion = '0.2.0'
groupId = 'net.gongmingqm10.uikit'
artifactId = 'bottom-tab'
desc = 'Android bottom tab'
}
3. 正式發(fā)布 jcenter
如上配置完成后碑隆,我們開(kāi)始正式發(fā)布 AAR 到 jcenter。在項(xiàng)目根目錄下蹬音,運(yùn)行 gradle 命令:
./gradlew clean install bintrayUpload
如果一切順利的話(huà)上煤,這一步將直接成功。如果出錯(cuò)著淆,請(qǐng)根據(jù)錯(cuò)誤信息重新診斷并修復(fù)劫狠。再次訪(fǎng)問(wèn) bintray/gongmingqm10/maven/bottom-tab 項(xiàng)目首頁(yè),你可以看到剛上傳的新版本永部。
{% img /images/bintray_6.png 上傳新版本成功 %}
上傳到個(gè)人倉(cāng)庫(kù)中独泞,可以看到右上方有一個(gè)地址 https://dl.bintray.com/gongmingqm10/maven
。這是個(gè)人的 maven 倉(cāng)庫(kù)地址苔埋,如果我們?cè)谠?$projectDir/build.gradle 添加此地址:
...
allprojects {
repositories {
jcenter()
maven {
url 'https://dl.bintray.com/gongmingqm10/maven/'
}
}
}
...
然后直接在 app/build.gradle 中懦砂,添加如下語(yǔ)句,則可以直接引用剛才上傳的 bottom-tab组橄。如果這種引用方式成功荞膘,說(shuō)明我們的 ./gradlew install bintrayUpload
這一步?jīng)]有問(wèn)題。
dependencies {
compile fileTree(include: ['*.jar'], dir: 'libs')
androidTestCompile('com.android.support.test.espresso:espresso-core:2.2.2', {
exclude group: 'com.android.support', module: 'support-annotations'
})
compile 'com.android.support:appcompat-v7:23.3.0'
testCompile 'junit:junit:4.12'
compile 'net.gongmingqm10.uikit:bottomtab:0.2.0'
// compile project(':bottomtab')
}
然而玉工,事情到這里并沒(méi)有完羽资。因?yàn)槲覀兪褂玫拇蟛糠值膸?kù)是不需要在 $projectDir/build.gradle 中做配置的。重新觀察 bottom-tab 這個(gè)主頁(yè)面遵班,右下角 linked to
可以點(diǎn)擊鏈接 Add to JCenter
屠升。這一步才是真正的發(fā)布 library 到 JCenter 中。然后我們需要做的就是等待 JCenter 官方團(tuán)隊(duì)的審核狭郑。一般兩三個(gè)工作日就可以審核通過(guò)腹暖。然后下一次引用,你就不需要添加私有的 maven 地址了愿阐。當(dāng)然如果你對(duì)這個(gè)庫(kù)有更新微服,也需要重新點(diǎn)擊 Add to JCenter趾疚。
所以最后的效果是 compile 'net.gongmingqm10.uikit:bottomtab:0.2.0'
可以一鍵引用我們新建的 Android 底部欄組件缨历,試用效果如下:
具體使用方法以蕴,請(qǐng)參考 BottomTab README。
項(xiàng)目地址:https://github.com/gongmingqm10/BottomTabAndroid