Android Bài 11: Cấu Hình Cho Gradle

Posted by

Được chỉnh sửa ngày 4/1/2017.

Chào mừng các bạn quay trở lại với bài học thứ 11 trong chương trình học Android của Yellow Code Books.

Bạn biết không, các thông tin liên quan đến cấu hình cho Gradle (chính là file build.gradle) và cấu hình cho Manifest (chính là file AndroidManifest.xml) đã được mình nhắc đến khá sớm ở Bài 5, tuy nhiên lời hứa đó mình đã nợ các bạn mãi tận hôm nay – Bài học Android thứ 11 – Mới có dịp được nói cụ thể về nó.

Và khi mình quyết định nói về chúng nó (GradleManifest), mình muốn nói cả hai trong cùng một bài viết, nhưng thấy có vẻ dài hơi quá nên mình sẽ ngắt chúng ra làm hai phần và nói ở hai bài khác nhau.

Đầu tiên cho mình có đôi lời về cả hai thằng này xíu (vì xém chút nữa chúng nằm chung một bài rồi). Thực ra thì hai thằng này chúng nó chẳng liên quan gì đến nhau hết á, chúng chẳng phải anh em họ hàng với nhau, thậm chí đến cả bạn bè cũng không. Nhưng khi nói đến Gradle thì không thể không nói đến Manifest. Bởi vì sao, chúng ta cùng quay về lịch sử một chút, bạn biết không, dân lập trình Android xưa kia cày cuốc trên nền Eclipse chỉ có biết đến cấu hình cho project thông qua Manifest, file này được mình liệt kê ở Bài 5 rồi nhé. Về sau khi công cụ cày cuốc được nâng cấp lên Android Studio, Manifest vẫn còn giữ nguyên vai trò của nó, tuy nhiên anh chàng Gradle được Android Studio giới thiệu sau này đã kiêm luôn một số việc của Manifest, khiến cho vai trò bị trộn lẫn. Mình nói vấn đề này để khi bạn đọc đâu đó thấy có nói phải khai báo ở Manifest, như khai báo version của app chẳng hạn, nhưng đọc chỗ khác lại thấy khai báo ở Gradle, thì đó là do ảnh hưởng của lịch sử bạn nhé.

Vai trò của bài hôm nay không phải làm bạn rối lên giữa Gradle và Manifest, cũng không phải một tiết học lịch sử. Mà bài học sẽ giúp bạn biết khi nào thì khai báo Gradle, khi nào thì khai báo Manifest một cách rõ ràng và chuyên nghiệp.

Uhm… Dù sao thì các bạn cũng cần biết đến khái niệm của 2 thằng này như nào phải không. Nhắc lại là chúng ta cùng nói đến Gradle trong bài hôm nay, và Manifest ở bài kế tiếp nhé.

Khái Niệm Gradle

Nói ngắn gọn thôi nhé, Gradle có thể hiểu như là một công cụ để build hệ thống, cũng giống như bạn nào đã từng sử dụng Ant như là một công cụ để build Android theo hướng command line vậy. Sau này khi Android Studio ra đời, Google đã tận dụng Gradle để phát triển Android plugin cho nó và thế là Android Studio có thể sử dụng được Gradle này để build các ứng dụng Android cho chúng ta.

Xong khái niệm rồi nhé, bạn nào chưa hiểu lắm muốn biết nhiều hơn thì xem thêm Gradle ở đây. Nhưng mình nghĩ không cần phải biết nhiều quá đâu. Gradle được tích hợp sẵn vào Android Studio, và được điều khiển một cách tự động thông qua Android Studio. Trước mắt bạn cần biết đủ để cấu hình cho Gradle thôi, cấu hình cho Gradle có nghĩa là bạn đang cấu hình cho project của mình, từ việc cấu hình version của công cụ để build, cho đến cấu hình version của app, chỉ định hệ điều hành Android mà ứng dụng hỗ trợ, khai báo thư viện từ bên ngoài… Bạn sẽ có dịp thực hành nhiều với Gradle và như vậy bạn sẽ ngày càng hiểu nó hơn. Tin mình đi!

Trước khi đi sâu vào Gradle bên dưới, mình cũng trình bày thêm rằng bài học hôm nay tập trung vào cách thức sử dụng Gradle có trong Android Studio. Có nghĩa là bạn có thể sử dụng Gradle độc lập ở đâu đó mà không cần phải có Android Studio vẫn được, nhưng nó thuộc về kiến thức khác mà bài học hôm nay xin phép chưa nói đến. Mình và các bạn vẫn phải dùng Android Studio để thực hành và xây dựng TourNote như mọi khi.

Làm Quen Với Gradle Wrapper

Chúng ta bắt đầu “vọc” Gradle bằng việc xem qua file Gradle Wrapper. Trong Android Studio bạn sẽ thấy file này nằm ở thư mục gradle/wrapper/. Tên file là gradle-wrapper.properties. Bạn có thể thấy file này như hình sau, hình trên máy bạn sẽ giống với hình bên trái hay bên phải là tùy vào cách view của cửa sổ này.

group

Bạn đừng ngần ngại, hãy click đúp vào file này để mở nó lên. Bạn đã thấy nội dung của Gradle Wrapper rồi đúng không nào, chúng rất ngắn… nhưng không kém phần quan trọng.

screen-shot-2016-12-15-at-17-22-14

Sở dĩ mình nói đến Gradle Wrapper đầu tiên, là vì file này sẽ chứa đường dẫn quyết định đến việc download Gradle ở đâu, và cả version của Gradle nữa, đường dẫn mình vừa nhắc đến hiển thị ở dòng distributionUrl. Thường thì khi tạo mới một project, Android đã để sẵn đường dẫn này cho bạn rồi nên bạn yên tâm không cần cấu hình gì cả. Có điều bạn nên biết đến file này, để sau này Android có nâng cấp version của Gradle, chính bạn là người phải sửa đường dẫn lại theo hướng dẫn của Google đấy nhé. File Gradle ở đường dẫn này sẽ được down về và install rồi để ở thư mục .gradle/ (có dấu chấm ở trước nhé). Không tin à, bạn cứ thử mở thư mục này ra xem.

screen-shot-2016-12-15-at-17-32-50

Làm Quen Với Các File Gradle

Yep đúng vậy, chúng ta chính thức làm quen với… các file Gradle“các”? Thật không vui là có đến hai file Gradle mà bạn cần phải biết và chúng đều có tên là build.gradle. Một file dùng cho cấu hình ở cấp độ project, còn một file dùng cho cấu hình ở cấp độ module. Tại sao lại chia ra làm hai cấp độ file thì bạn hãy xem tiếp bên dưới nhé.

group

build.gradle Ở Cấp Độ Project

Theo đường dẫn ở hình trên, bạn click đúp để mở build.gradle ở cấp độ project lên xem trước. File này sẽ cấu hình cho tất cả các module bên trong project của bạn. Thông thường thì các project chỉ có một module mà thôi, vẫn có project có nhiều module nhưng ở giai đoạn này bạn không cần quan tâm lắm với việc này, chúng ta sẽ nói đến project nhiều module ở phần riêng.

screen-shot-2016-12-15-at-18-17-53

build.gradle ở cấp độ này cũng không có nhiều thứ để nói, tuy nhiên mình có thể điểm sơ qua cho các bạn nắm rõ cách thức cấu hình file này như sau.

– Mỗi một mục buildscript, allprojects, task clean trong file này được gọi là một closure, chúng ta tạm gọi là các khối.
Khối buildscript diễn đạt… uhm… bạn cứ xem như là nó đưa ra một kịch bản cho biết cần phải download phiên bản gradle ở đâu về, cụ thể trong khối này nó định nghĩa repositories là ở jcenter() (hàm jcenter() này giúp định nghĩa thông tin về repository cho Maven Central, một nơi thu thập các dependencies mã nguồn mở). Trong khối buildscript này còn có khối con dependencies là nơi liệt kê các thư viện dùng chung cho project, như hiện tại bạn thấy nó khai báo sẽ dùng một thư viện gradle, với thông tin về đường dẫn và version của gradle cần down.
Khối allprojects là nơi định nghĩa các thiết lập cho tất cả project. Trong trường hợp này nó đang định nghĩa jcenter() là repositories để tìm tất cả các thư việc cần thiết cho các module bên trong project này.

Phần thông tin còn lại nếu có trong file này, bạn cứ để như mặc định. Thường thì mình cũng ít đụng vào file này, chỉ nói sơ qua cho các bạn hiểu chút đỉnh thôi. File build.gradle kế tiếp này mới thực sự quan trọng nè.

build.gradle Ở Cấp Độ Module

Bạn hãy mở file build.gradle ở cấp độ module này lên nhé (theo đường dẫn đến thư mục như hình trên đây). Như tên gọi, thì file này sẽ cấu hình cho từng module trong project, nên nó sẽ được sử dụng nhiều hơn.

screen-shot-2016-12-16-at-07-57-01

Mình sẽ nói đến từng closure (khối) trong file này bằng những mục riêng bên dưới chứ không phải bằng các gạch đầu dòng, vì thông tin ở file này sẽ khá nhiều.

Khối android

Chà khối này định nghĩa rất nhiều cấu hình cho project của bạn (tuy build.gradle này dành để cấu hình cho module, nhưng vì project của chúng ta thường chỉ có một module, nên mình nói luôn là cấu hình này là cấu hình cho project cũng được bạn nhé).

compiledSdkVersion: giá trị ở mục này chính là version của Android mà bạn muốn chỉ định để project của bạn build ra. Nghe có vẻ lạ phải không nào, mới đầu làm quen với Android mình cũng lùng bùng lỗ tai chỗ này, mất bao nhiêu lâu mới phân biệt rõ ràng. Để mình giúp bạn rõ. Chúng ta đã biết minSdkVersion là thông số version Android nhỏ nhất mà project của bạn hỗ trợ, thông số này bạn biết rồi nhé, lúc bạn tạo mới project í, nhớ không, bạn nào quên thì xem lại Bài 3 nhé. Rồi chúng ta lại có targetSdkVersion là version Android mới nhất mà project của bạn hỗ trợ, cái này mình nói sau. Nhưng bạn nên biết là cho dù project của bạn hỗ trợ Android trễ nhất và mới nhất như nào thì khi build, project của bạn vẫn phải dựa vào một version Android cụ thể để nó còn biết gắn các thư viện hỗ trợ vào, chính vì vậy mà compiledSdkVersion ra đời. Theo mặc định thì giá trị này sẽ được thiết lập là version Android lớn nhất (giống với version ở targetSdkVersion). Bạn hoàn toàn có thể chỉ định một version thấp hơn version của target, nhưng compile với một version lớn nhất sẽ cho phép ứng dụng của bạn có được các thư viện Android mới nhất, như giao diện của Android 7.0 chẳng hạn, giúp tạo trải nghiệm tốt nhất cho user.
buildToolsVersion: giá trị ở mục này chỉ định version của công cụ build Android (Android SDK build tool). Giá trị này bạn không cần quan tâm lắm, mặc dù nó cũng khá quan trọng, nhưng thông thường bạn được Android Studio hỗ trợ. Để mình nhớ lại xem thông số này có thực sự là một vấn đề không, nếu có thì chắc chắn sẽ có một bài viết riêng về nó đấy nhé.
applicationId: thông số này nằm bên trong khối defaultConfig, cũng như bao thông số khác bên trong khối này, chúng giúp định nghĩa một số cấu hình default ban đầu, dĩ nhiên bạn có thể sửa được, và chắc chắn chúng ta sẽ thực hành sửa chữa mục này ở phần kế tiếp của bài học. Thông số applicationId này mặc định chính là package name. Chà chà bạn còn nhớ hay đã quên, vui lòng xem lại Bài 3 nếu bạn quên package name có ý nghĩa là gì nhé nhé.
minSdkVersion: đã được nhắc ở mục compiledSdkVersion trên đây rồi nhé bạn.
targetSdkVersion: cũng đã được nhắc đến ở trên rồi nhé, thông số này được tạo mặc định nên ban đầu bạn không cần chú ý lắm, về sau nếu cần hỗ trợ Android mới nhất thì nhớ nâng em này với em compiledSdkVersion lên. À có lẽ mình quên nói là các version của Android dùng cho compiledSdkVersion, minSdkVersiontargetSdkVersion đều là các con số và chúng được tham chiếu dựa trên bảng này, các bạn vào tham khảo nhé.
versionCodeversionName: dễ hiểu thôi, versionName là version của app sẽ được Google Play hiện ra khi user chuẩn bị download và install app, versionName còn được hiển thị trong Setting của app nữa, dù vậy versionName cũng chỉ hiển thị cho user biết thôi, nó không mang ý nghĩa so sánh gì cả. Trong khi đó versionCode thì dùng để hệ thống biết các phiên bản cập nhật của app, versionCode được set ban đầu là 1, nếu bạn xuất bản những bản cập nhật của app lên Google Play, bạn phải nâng versionCode, trong khi versionName như thế nào Google cũng không quan tâm.

Khối dependencies

Khối dependencies này cũng giống như khối dependencies dùng trong buildscript ở file build.gradle cấp độ project đã nói ở trên đây, là đều dùng để định nghĩa ra các thư viện. Chúng chỉ khác nhau ở chỗ một thằng định nghĩa thư viện dùng chung cho project, còn một thằng định nghĩa thư viện cho từng module.

Bạn nhìn xem có khá nhiều thư viện được định nghĩa sẵn trong đây, tùy vào thời điểm bạn tạo project mà hệ thống quyết định project của bạn nên có những thư viện nào.

Chúng ta sẽ cùng nhau thực hành trên TourNote về cách sử dụng dependencies này cũng như các thuộc tính khác trong Gradle ở phần dưới nhé.

Thực Hành Cấu Hình Gradle Cho TourNote

Bài thực hành này chúng ta sẽ cấu hình Gradle cho project TourNote, bài thực hành này sẽ rất quan trọng, vì nếu chúng ta không thực hiện bài này, buổi học sau các bạn sẽ gặp khó khăn khi bổ sung các thành phần UI cho TourNote.

Tại sao quan trọng thì các bạn hãy thực hiện nhé.

Thay Đổi Version Của Ứng Dụng

Chúng ta đã nói đến hai thuộc tính liên quan đến quản lý version bên trong ứng dụng, hai thuộc tính này là versionCodeversionName, chúng nằm ở file build.gradle của cấp độ module. Nếu bạn mở file này lên, bạn sẽ thấy hiện tại versionCode đang là 1versionName đang là “1.0”.

Với mỗi lần submit app lên Google Play, bạn nên nâng số versionCode lên một đơn vị (lưu ý giá trị này là số nguyên nhé), nếu bạn không nâng số này lên thì Google Play sẽ không cho bạn submit app đâu nhé. Nhưng với bài thực hành này chúng ta không publish app do đó chúng ta sẽ chỉ cần quan tâm đến versionName mà thôi.

Giả sử chúng ta cung cấp đến user một version có 3 phần “x.y.z”. Version đầu tiên của app sẽ là “1.0.0”. Nếu có thay đổi lớn trong app chúng ta sẽ nâng số ở phần x lên 1 đơn vị, tương tự với thay đổi vừa sẽ nâng số y lên 1 đơn vị, và thay đổi nhỏ sẽ nâng z. Nên nhớ là versionName được đặt thoải mái vì đây là kiểu String, nên bạn có thể đặt các ký tự vào đây, miễn sao user hay ai đó hiểu được ý nghĩa của version này.

Vậy bạn hãy mở file build.gradle cấp module và sửa version của app như sau.

apply plugin: 'com.android.application'

android {
    compileSdkVersion 24
    buildToolsVersion "24.0.2"
    defaultConfig {
        applicationId "com.yellowcode.tournote"
        minSdkVersion 15
        targetSdkVersion 24
        versionCode 1
        versionName "1.0.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:24.2.1'
    testCompile 'junit:junit:4.12'
}

Bạn thấy rằng bất kỳ chỉnh sửa gì trên file build.gradle, thì hệ thống đều xuất hiện thông báo yêu cầu bạn phải đồng bộ (sync) lại project.

Screen Shot 2016-12-16 at 12.34.21.png

Bạn chỉ cần nhấn vào Sync Now ở bên phải vạch vàng phía trên và đợi trong giây lát. Trong lúc đang đồng bộ hệ thống cũng có thông báo trạng thái.

screen-shot-2016-12-16-at-12-36-07

Sau khi đồng bộ xong, bạn hãy run ứng dụng lên thiết bị. Rồi mở Settings, vào xem thông tin của ứng dụng TourNote, bạn sẽ thấy version mà chúng ta vừa thay đổi được hiển thị như sau.

device-2016-12-16-124255

Và nếu ứng dụng của bạn có được đưa lên Google Play, versionName sẽ xuất hiện như sau (cái này mình nhờ lấy một app khác show giúp, chứ ứng dụng của chúng ta còn chưa đâu vào đâu, làm sao mà đưa lên Google Play).

device-2016-12-16-125039

Thêm Thư Viện Cho Ứng Dụng

Thư viện (library) là một tập hợp các source code và resource được đóng gói và cung cấp bởi chính Google hoặc các nhà cung cấp ở bên thứ 3. Các thư viện này được xây dựng ra nhằm mục đích cung cấp thêm cho bạn có được những trợ giúp về mặt UI hay chức năng, mà bạn không cần phải xây dựng lại từ đầu.

Như đã nói, những nguồn cung cấp thư viện có thể chính là Google hoặc bên thứ 3. Chúng ta sẽ nói kỹ hơn về thư viện ở bài khác. Nhưng trong bài thực hành này, chúng ta phải làm sao để vào trong project hai thư viện để bài thực hành sau chúng ta có sẵn cơ sở mà đi tiếp. Hai thư viện đó là com.android.support:design (hỗ trợ hiển thị Floating Action Button) và com.android.support:recyclerview (hỗ trợ hiển thị list). Bạn chưa cần biết chúng là gì đâu, bài sau mình sẽ nói rõ hơn chút xíu.

Giờ bạn hãy tiếp tục chỉnh sửa file build.gradle cấp module bằng cách thêm hai dòng sau vào khối dependencies.

compile 'com.android.support:design:24.2.0'
compile 'com.android.support:recyclerview-v7:24.2.0'

File build.gradle sau khi thêm vào như sau.

apply plugin: 'com.android.application'

android {
    compileSdkVersion 24
    buildToolsVersion "24.0.2"
    defaultConfig {
        applicationId "com.yellowcode.tournote"
        minSdkVersion 15
        targetSdkVersion 24
        versionCode 1
        versionName "1.0.0"
        testInstrumentationRunner "android.support.test.runner.AndroidJUnitRunner"
    }
    buildTypes {
        release {
            minifyEnabled false
            proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'
        }
    }
}

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:24.2.1'
    testCompile 'junit:junit:4.12'
    compile 'com.android.support:design:24.2.0'
    compile 'com.android.support:recyclerview-v7:24.2.0'
}

Và chắc chắn bạn phải sync lại project rồi. Sau đó bạn cứ run ứng dụng lên nhưng sẽ chưa có chuyện gì thay đổi ở bước thực hành này hết nhé. Bài học sau bạn sẽ biết sức mạnh của bước thực hành hôm nay.

Download Source Code Mẫu

Bạn có thể download source code mẫu của bài này ở đây.

Bài này hơi dài đúng không nào, mình biết với bạn mới bắt đầu Android, bài này có thể là một sự tiếp cận hơi khó khăn. Nhưng bạn yên tâm nhé, bạn sẽ đụng đến việc cấu hình này hơi bị nhiều đấy, và bạn sẽ quen dần thôi.

Cảm ơn bạn đã đọc các bài viết của Yellow Code Books. Bạn hãy đánh giá 5 sao nếu thấy thích bài viết, hãy comment bên dưới nếu có thắc mắc, hãy để lại địa chỉ email của bạn để nhận được thông báo mới nhất khi có bài viết mới, và nhớ chia sẻ các bài viết của Yellow Code Books đến nhiều người khác nữa nhé.

Bài Kế Tiếp

Bạn sẽ làm quen đến việc cấu hình Manifest, cũng sẽ hơi khó khăn một chút nhưng vượt qua kiến thức này bạn đã bước lên một nấc thang mới trong giấc mơ lập trình Android của mình rồi đấy.

Advertisements
Rating: 5.0/5. From 13 votes.
Please wait...

7 comments

  1. Chào Bạn :
    Ở bài này phần thêm thư viện cho Ứng dụng thì Mình hiểu do Ver của Mình đã thay đổi lên 25.3.1 ( Do thời điểm Mình học bây giờ thì phần mềm đã cập nhật lên 25.3.1 ) theo như trong file Grabdle có dòng lệnh đã ghi như vậy.
    So với của Bạn là 24.2.0 nên Mình copy 2 dòng lệnh như Bạn hướng dẫn và sửa lại tương ứng.
    Mình muốn hỏi muốn biết Ver đó thì Mình sẽ tìm ở đâu trong trường hợp Mình không xem file Gradle.

    1. Chào bạn Thuận, do Android thay đổi nhiều thứ quá nên mình chưa có thời gian quay lại các bài học trước để điều chỉnh cho hợp lý.
      Bạn Thuận có thể xem trước một tí ở Bài 17, ở phần thực hành của bài 17 này mình đã phát hiện ra thư viện của project cần phải được cập nhật và mình có hướng dẫn các bạn nâng cấp như thế nào nhé, bạn tìm đến phần “Cảnh Báo!Cập Nhật Project”.
      Cảm ơn bạn đã comment nhé.

  2. Chào admin, mình đang gặp vấn đề khi config cho grade với :

    compileSdkVersion 25
    buildToolsVersion ‘25.0.2’
    targetSdkVersion 25

    Và dependencies {
    . …
    compile ‘com.android.support:appcompat-v7:25.1.1’ ( Báo lỗi com.android.support libraries must use the exact same version specification)
    }

    Thấy báo lỗi đỏ, mà vẫn build dược ứng dụng, không biết fix thế nào bạn nhỉ?

    Lỗi của mình : https://ibb.co/nP90hG

    1. Chào bạn Đạt.

      Lỗi này xảy ra khi bạn khai báo thư viện appcompat-v7 là version 25.1.1, mà các thư viện khác trong gói support lại không cùng version. Theo như thông báo lỗi thì bạn có thể thấy gói animated-vector-drawable:25.3.1 và customtabs:25.0.0 đều bị lệch version so với gói appcompat-v7 hết. Có thể gradle của project của bạn không có khai báo các gói này, nhưng ở đâu đó trong các thư viện bạn đang sử dụng có khai báo.

      Cách giải quyết là bạn nên khai báo lại các thư viện bị lệch version trên kia ở ngay file build.gradle này, chúng sẽ bao gồm các dòng sau:
      – compile ‘com.android.support:appcompat-v7:25.1.1’
      – compile ‘com.android.support:animated-vector-drawable:25.1.1’
      – compile ‘com.android.support:customtab:25.1.1’

      Nếu thay đổi như thế này rồi mà còn báo lỗi ở gói nào nữa thì bạn cứ liệt kê ra cho bằng hết nhé.

Gửi phản hồi