App Connect With Remote API


ধরা যাক, একটা এপ্লিকেশন রিমোট সার্ভার এর কাছ থেকে API এর মাধমে ডাটা প্রদান করবে। Retrofit লাইব্রেরি  ব্যবহার করে এনড্রয়েড অ্যাপ্লিকেশন এ রিমোট সার্ভার এর সাথে HTTP  দিয়ে API কল করে কাজ করানো যায়। এটা করার জন্য নিচের কাজ করতে হবে 


১।মডিউল লেভেল  build.gradle.kts এ ডিপেন্ডেন্সি যুক্ত করতে হবে

    // Retrofit
    implementation("com.squareup.retrofit2:retrofit:2.9.0")
    implementation("com.squareup.retrofit2:converter-gson:2.9.0")
    implementation("com.squareup.okhttp3:okhttp:4.12.0")
    implementation("com.squareup.okhttp3:logging-interceptor:4.12.0")
    implementation("com.google.code.gson:gson:2.10")


২। OK  HTTP ক্লায়েন্ট সেটআপ করতে হবে 

@Module
@InstallIn(SingletonComponent::class)
class ApiConfig {

    @Singleton
    @Provides
    fun providesOkHttpClient(
        memoryAuthInterceptor: MemoryAuthInterceptor,
        ) = OkHttpClient.Builder()
        .addInterceptor(HttpLoggingInterceptor().setLevel(HttpLoggingInterceptor.Level.HEADERS))
        .addInterceptor(HttpLoggingInterceptor().setLevel(HttpLoggingInterceptor.Level.BODY))
        .addInterceptor(memoryAuthInterceptor)
        .build()

    @Provides
    @Singleton
    fun provideReminderService(retrofit: Retrofit): ReminderApi =
        retrofit.create(ReminderApi::class.java)
}


৩। API এর ইন্টারফেস তৈরি করতে হবে 

interface ReminderApi {
    @GET("api/private/reminders")
    suspend fun findAll(): Response<List<Reminder>>

    @GET("api/private/reminders/{id}")
    suspend fun findById(@Path("id") id: String): Response<Reminder>

    @POST("api/private/reminders")
    suspend fun create(@Body reminder: Reminder): Response<Reminder>

    @PUT("api/private/reminders")
    suspend fun update(@Body reminder: Reminder): Response<Reminder>

    @DELETE("api/private/reminders/{id}")
    suspend fun delete(@Path("id") id: String): Response<Unit>
}


৪। Repository থেকে API কল করে কাজ করাতে হবে 

class ReminderRepository @Inject constructor(
  private val reminderApi: ReminderApi
) {

    suspend fun getAll(): ApiResponse<List<Reminder>> {
        return processResponse(reminderApi.findAll())
    }

    suspend fun getById(id: String): ApiResponse<Reminder> {
        return processResponse(reminderApi.findById(id))
    }

    suspend fun save(reminder: Reminder): ApiResponse<Reminder> {
        return if (reminder.id == null) {
            processResponse(reminderApi.create(reminder))
        } else {
            processResponse(reminderApi.update(reminder))
        }
    }

    suspend fun delete(id: String): ApiResponse<Unit> {
        return processResponse(reminderApi.delete(id))
    }
}

৫। ViewModel এসিঙ্ক রিপোজিটরি থেকে ডাটা পড়তে হবে 

@HiltViewModel
class ReminderViewModel @Inject constructor(
    private val reminderRepository: ReminderRepository
) : ViewModel() {

    private val _reminderList = MutableStateFlow(listOf<Reminder>())
    val reminderList = _reminderList

    val isLoading = MutableStateFlow(false)
    val error = MutableStateFlow<ApiResponse.Error?>(null)


    fun findAll() {
        isLoading.value = true
        viewModelScope.launch {
            try {
                when (val result = reminderRepository.getAll()) {
                    is ApiResponse.Success -> {
                        _reminderList.value = result.data
                        isLoading.value = false
                    }
                    is ApiResponse.Error -> {
                        error.value = ApiResponse.Error(result.status, result.message, result.errors)
                        isLoading.value = false
                    }
                }
            } catch (e: Exception) {
                Log.d("ReminderViewModel", "getAll: ${e.cause}")
                error.value = generateServerError(e)
                isLoading.value = false
            }
        }
    }
}