Retrieve and Display data from the Internet into your Android App with Retrofit.

Retrieve and Display data from the Internet into your Android App with Retrofit.

In this tutorial, we'll build an app that connects to a web service to retrieve and display data. We'll be using the Retrofit library to connect to a REST web service on the internet and get a response. For now, we focus on displaying raw JSON. And of course, we'll be using Android Studio as our IDE.

Step 1: Create a new project and call it DisplayData

  • Open Android Studio if it is not already opened.
  • In the main Welcome to Android Studio dialog, click Start a new Android Studio project.
  • The Choose your project dialog appears. Select Empty Activity as shown below, and click Next.
  • In the Configure your project dialog, enter "DisplayData" for the Name and click Finish

Step 2: Add various dependencies:

  • Inside the dependencies block, add the Gradle dependency for the Retrofit and ViewModel.
//Retrofit
implementation "com.squareup.retrofit2:retrofit:2.9.0"
implementation "com.squareup.retrofit2:converter-scalars:2.9.0"
//ViewModel
implementation "androidx.lifecycle:lifecycle-viewmodel-ktx:2.2.0"
  • Add the data binding dependency to Gradle
android{...

    buildFeatures {
        dataBinding true
    }
  • Apply the kotlin-kapt plugin at the top of the build.gradle file
 id 'kotlin-kapt'
  • Ensure the support for Java 8 language features are added
compileOptions {
    sourceCompatibility JavaVersion.VERSION_1_8
    targetCompatibility JavaVersion.VERSION_1_8
}
kotlinOptions {
    jvmTarget = '1.8'
}

Click on Sync Now

Step 3: Setup ViewModel and connect with MainActivity

  • Create a new Kotlin class called DisplayDataViewModel class and make the class extend the abstract class ViewModel
class OverviewViewModel : ViewModel() {
}
  • In DisplayDataViewModel, we create both internal and external LiveData for the response String
private val _response = MutableLiveData<String>()

val response: LiveData<String>
    get() = _response
  • At the top of MainActivity class, make the MainActivity lazily initializes the DisplayDataViewModel.
private val viewModel: DisplayDataViewModel by lazy {
    ViewModelProvider(this).get(DisplayDataViewModel::class.java)
}
  • Inside the onCreateView() method. Inflate the MainActivity layout using data binding. Comment out or delete the setContentView line of code.
//setContentView(R.layout.activity_main)
val binding: ActivityMainBinding =
    DataBindingUtil.setContentView(this, R.layout.activity_main)
  • In the activity_main.xml layout, add the data binding for the view model. This imports DisplayDataViewModel. (Make layout view the root view).
<layout ...>
    <data>
        <variable
            name="displayDataViewModel"
            type="com.example.marsproperty.DisplayDataViewModel" />
    </data>
</layout>
  • Create the Constraintlayout, and add the TextView inside. Bind the response from the ViewModel to the TextView
<androidx.constraintlayout.widget.ConstraintLayout
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        tools:context=".MainActivity">
    <TextView
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="@{displayDataViewModel.response}"
        app:layout_constraintBottom_toBottomOf="parent"
        app:layout_constraintLeft_toLeftOf="parent"
        app:layout_constraintRight_toRightOf="parent"
        app:layout_constraintTop_toTopOf="parent" />
</androidx.constraintlayout.widget.ConstraintLayout>
  • Inside the MainActivity file, Specify the MainActivity view as the lifecycle owner of the binding and pass the displayDataViewModel into the data binding.
binding.lifecycleOwner = this
binding.displayDataViewModel = viewModel

Step 4: Implement the DisplayDataApiService

  • Create DisplayDataApiService.kt and add a constant Base Url at the top of the file.
private const val BASE_URL = "https://jsonplaceholder.typicode.com/"
  • Below the constant, use a Retrofit builder to create a Retrofit object
private val retrofit = Retrofit.Builder()
   .addConverterFactory(ScalarsConverterFactory.create())
   .baseUrl(BASE_URL)
   .build()
  • Just below the call to the Retrofit builder, define an interface that defines how Retrofit talks to the web server using HTTP requests.
interface DisplayDataApiService {
    @GET("todos")
    fun getProperties():
            Call<String>
}
  • Below the DisplayDataApiService interface, define a public object called DataApi to initialize the Retrofit service.
object DataApi {
    val retrofitService : DisplayDataApiService by lazy { 
       retrofit.create(DisplayDataApiService::class.java) }
}

Step 5: Call the web service in DisplayDataViewModel.

  • In the DisplayDataViewModel, we create the init block and call getDetails() method inside.
init {
    getDetails()
}
  • Create the getDetails method
private fun getDetails() {

}
  • Next we'll call the web service in DisplayDataViewModel. Inside the getDetails() method, add the code below,
DataApi.retrofitService.getProperties().enqueue( 
   object: Callback<String> {
})
  • Click on the word object, which is underlined in red. Select Code > Implement methods. Select both onResponse() and onFailure() from the list.
override fun onFailure(call: Call<String>, t: Throwable) {
       TODO("not implemented") 
}

override fun onResponse(call: Call<String>, 
   response: Response<String>) {
       TODO("not implemented") 
}
  • In onFailure(), delete the TODO and set the _response to a failure message, as shown below.
override fun onFailure(call: Call<String>, t: Throwable) {
   _response.value = "Failure: " + t.message
}
  • In onResponse(), delete the TODO and set the _response to the response body.
override fun onResponse(call: Call<String>, 
   response: Response<String>) {
      _response.value = response.body()
}

Step 6: Define the internet permission.

Open app/manifests/AndroidManifest.xml. Add this line just before the tag:

<uses-permission android:name="android.permission.INTERNET" />

Compile and run the app. If everything is working correctly with your internet connection, you see...

Screenshot_1607409656a.png Cover photo by Luca Bravo on Unsplash