def retrofitVersion = "2.9.0"
implementation "com.squareup.retrofit2:retrofit:$retrofitVersion"
implementation "com.squareup.retrofit2:converter-gson:$retrofitVersion"
Check the latest version from here: https://github.com/square/retrofit#download
Add coroutine if not already added
// Base URL - Must have an ending slash
// ==========================================================================
val BASE_URL = "https://food2fork.ca/api/"
// MODEL classes
// ==========================================================================
// Model class, JSON response
// from network will be mapped
// to this class.
data class ResponseMain(
val count: Int,
val next: String,
val previous: String,
val results: List
)
// Another model class.
// The main JSON response contains
// a list of other JSON objects
// using key: "results".
// This class is used for those
// JSON objets.
data class ResponseIndividualRecipe(
val cooking_instructions: Any,
val description: String,
val featured_image: String,
val ingredients: List,
val rating: Int,
val source_url: String,
val title: String
)
// There can be many other model classes
// as required to map JSON response.
// ==========================================================================
// RETROFIT interface
// Interface functions MUST be suspend functions.
// Function return type - data model class.
// ==========================================================================
// The interface outlines the methods
// to be called for network operations.
// Methods are implemented by retrofit,
// we only need to provide some information
// using annotations.
// @GET - takes the api end point
// @Header - takes info like token
// @Query - marks query parameters
// Example: https://food2fork.ca/api/recipe/search/?page=2&query=chicken
// Base URL - https://food2fork.ca/api/
// End point - recipe/search
// Query parameters : "page", "query"
interface RetrofitInterface {
@GET("recipe/search/")
suspend fun queryByRecipes(
@Header("Authorization") token: String,
@Query("page") pageNo: Int,
@Query("query") recipes: String
): ResponseMain
// There can be other methods
// for GET requests or even
// PUT, POST, DELETE requests
}
// ==========================================================================
// RETROFIT Service object
// ==========================================================================
// Should have the base url,
// converter used here is Gson
// (Converts JSON to Model classes).
// Finally create() takes the
// name of the interface.
val RetrofitService = Retrofit.Builder()
.baseUrl(BASE_URL)
.addConverterFactory(GsonConverterFactory.create())
.build()
.create(RetrofitInterface::class.java)
// ==========================================================================
// Make the network call - from a coroutine scope.
// ==========================================================================
class MainActivity: AppCompatActivity() {
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
CoroutineScope(IO).launch {
val response = RetrofitService.queryByRecipes(
token = "Token 9c8b06d329136da358c2d00e76946b0111ce2c48",
pageNo = 1,
recipes = "beef"
)
println("Result from network: ${response.results.size}")
}
}
}
// ==========================================================================
// MODEL classes - same as above.
// Retrofit service object - same as above
// Retrofit interface
// Functions MUST NOT be suspend functions.
// They must return a type Call
// ==========================================================================
interface RetrofitInterface {
@GET("recipe/search/")
fun queryByRecipesByCall(
@Header("Authorization") token: String,
@Query("page") pageNo: Int,
@Query("query") recipes: String
): Call
}
// ==========================================================================
// Make the network call, get the response using callback
// ==========================================================================
val networkCall = RetrofitService.queryByRecipesByCall(
token = "Token 9c8b06d329136da358c2d00e76946b0111ce2c48",
pageNo = 1,
recipes = "beef"
)
// enqueue methods puts the request
// on a queue for retrofit to execute.
// Once the call is executed the callback
// methods are called.
networkCall.enqueue(object : Callback {
override fun onResponse(call: Call, response: Response) {
println("Result from network: ${response.body()?.results?.size}")
}
override fun onFailure(call: Call, t: Throwable) {
}
})
// ==========================================================================