Skip to content

Commit

Permalink
Create BoardApiService.kt by Retrofit and DI
Browse files Browse the repository at this point in the history
  • Loading branch information
ininmm committed Jan 31, 2021
1 parent 55da0e6 commit 15a0094
Show file tree
Hide file tree
Showing 32 changed files with 189 additions and 77 deletions.
23 changes: 21 additions & 2 deletions app/build.gradle
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,8 @@ android {
targetSdkVersion buildConfig.targetSDK
versionCode buildConfig.versionCode
versionName buildConfig.versionName
buildConfigField "String", "API_Domain", "\"${apiDomain()}\""
buildConfigField "String", "API_Domain", "\"${domain()}\""
buildConfigField "String", "develop_domain", "\"${developDomain()}\""
buildConfigField "String", "demo_hot_article_url", "\"${demoHotArticleUrl()}\""
testInstrumentationRunner buildConfig.runner
ndk {
Expand Down Expand Up @@ -45,7 +46,7 @@ android {
}
}

def apiDomain() {
def domain() {
def path = getRootProject().file('api.properties')
if (path.canRead()) {
def props = new Properties()
Expand All @@ -61,6 +62,22 @@ def apiDomain() {
}
}

def developDomain() {
def path = getRootProject().file('api.properties')
if (path.canRead()) {
def props = new Properties()
props.load(new FileInputStream(path))
if (props != null) {
return props['api_domain']
} else {
println 'some entries in \\\'api.properties\\\' not found!'
}
} else {
println 'Use CI Variables'
return System.getenv('api_domain')
}
}

static def demoHotArticleUrl(){
return "https://www.google.com.tw/"
}
Expand Down Expand Up @@ -106,6 +123,8 @@ dependencies {
// Square
implementation deps.square.okhttp
implementation deps.square.okio
implementation deps.square.retrofit.core
implementation deps.square.retrofit.gsonConverter

testImplementation deps.google.truth
testImplementation deps.junit
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@ import android.widget.TextView
import androidx.appcompat.widget.AppCompatImageButton
import androidx.recyclerview.widget.RecyclerView
import tw.y_studio.ptt.R
import tw.y_studio.ptt.model.HotBoardsItem
import tw.y_studio.ptt.api.model.hot_board.HotBoardsItem
import tw.y_studio.ptt.ptt.PttColor

class HotBoardsListAdapter(
Expand Down Expand Up @@ -36,7 +36,7 @@ class HotBoardsListAdapter(
when (getItemViewType(position)) {
TYPE_NORMAL -> {
(holder as? ViewHolder)?.apply {
textViewTitle.text = data[position].title
textViewTitle.text = data[position].boardName
textViewSubtitle.text = data[position].subtitle
textViewOnlinePeople.text = data[position].online
person.setColorFilter(
Expand All @@ -49,7 +49,7 @@ class HotBoardsListAdapter(
}
TYPE_EDIT -> {
(holder as? ViewHolderEdit)?.apply {
textViewTitle.text = data[position].title
textViewTitle.text = data[position].boardName
textViewSubtitle.text = data[position].subtitle
textViewOnlinePeople.text = data[position].online
itemView.setOnClickListener { onItemClickListener.onItemClick(data[position]) }
Expand Down
9 changes: 4 additions & 5 deletions app/src/main/java/tw/y_studio/ptt/api/PopularBoardListAPI.kt
Original file line number Diff line number Diff line change
Expand Up @@ -2,14 +2,13 @@ package tw.y_studio.ptt.api

import okhttp3.Request
import org.json.JSONArray
import tw.y_studio.ptt.model.HotBoard
import java.util.*
import tw.y_studio.ptt.api.model.hot_board.HotBoardTemp

class PopularBoardListAPI : BaseAPIHelper(), IBaseAPI {
private val _data: MutableList<HotBoard> = mutableListOf()
private val _data: MutableList<HotBoardTemp> = mutableListOf()

@Throws(Exception::class)
fun refresh(page: Int, count: Int): MutableList<HotBoard> {
fun refresh(page: Int, count: Int): MutableList<HotBoardTemp> {
_data.clear()
val request = Request.Builder()
.url("$hostUrl/api/Board/Popular?page=$page&count=$count")
Expand All @@ -29,7 +28,7 @@ class PopularBoardListAPI : BaseAPIHelper(), IBaseAPI {
while (!list.isNull(i)) {
val m3 = list.getJSONObject(i)
i++
val hotboard = HotBoard(
val hotboard = HotBoardTemp(
number = m3.getInt("sn"),
title = m3.getString("name"),
subtitle = m3.getString("title"),
Expand Down
6 changes: 3 additions & 3 deletions app/src/main/java/tw/y_studio/ptt/api/PostAPI.kt
Original file line number Diff line number Diff line change
Expand Up @@ -6,9 +6,9 @@ import okhttp3.FormBody
import okhttp3.Request
import okhttp3.RequestBody
import org.json.JSONObject
import tw.y_studio.ptt.model.PartialPost
import tw.y_studio.ptt.model.Post
import tw.y_studio.ptt.model.PostRank
import tw.y_studio.ptt.api.model.PartialPost
import tw.y_studio.ptt.api.model.Post
import tw.y_studio.ptt.api.model.PostRank
import tw.y_studio.ptt.utils.Log
import tw.y_studio.ptt.utils.model.PartialPostTypeAdapter
import tw.y_studio.ptt.utils.model.PostTypeAdapter
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
package tw.y_studio.ptt.api.board

import retrofit2.http.GET
import tw.y_studio.ptt.api.model.hot_board.HotBoard

interface BoardApiService {
@GET("api/boards/popular")
suspend fun getPopularBoard(): HotBoard
}
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
package tw.y_studio.ptt.model
package tw.y_studio.ptt.api.model

data class Comment(
val userid: String,
Expand Down
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
package tw.y_studio.ptt.model
package tw.y_studio.ptt.api.model

data class PartialPost(
val title: String = "",
Expand Down
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
package tw.y_studio.ptt.model
package tw.y_studio.ptt.api.model

data class Post(
val title: String,
Expand Down
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
package tw.y_studio.ptt.model
package tw.y_studio.ptt.api.model

data class PostRank(
val board: String,
Expand Down
39 changes: 39 additions & 0 deletions app/src/main/java/tw/y_studio/ptt/api/model/hot_board/HotBoard.kt
Original file line number Diff line number Diff line change
@@ -0,0 +1,39 @@
package tw.y_studio.ptt.api.model.hot_board

import com.google.gson.annotations.SerializedName

data class HotBoard(
@SerializedName("list")
val list: List<Board>,
@SerializedName("next_idx")
val nextId: String
)

data class Board(
@SerializedName("bid")
val boardId: String,
@SerializedName("brdname")
val boardName: String,
@SerializedName("class")
val boardClass: String,
@SerializedName("flag")
val boardAttributes: Int,
@SerializedName("last_post_time")
val lastPostTime: Int,
@SerializedName("moderators")
val moderators: List<String>,
@SerializedName("nuser")
val onlineUser: Int,
@SerializedName("read")
val read: Boolean,
@SerializedName("reason")
val reason: String,
@SerializedName("stat_attr")
val stateAttributes: Int,
@SerializedName("title")
val title: String,
@SerializedName("total")
val totalArticles: Int,
@SerializedName("type")
val type: String
)
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
package tw.y_studio.ptt.model
package tw.y_studio.ptt.api.model.hot_board

data class HotBoard(
data class HotBoardTemp(
val number: Int,
val title: String,
val subtitle: String,
Expand Down
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
package tw.y_studio.ptt.model
package tw.y_studio.ptt.api.model.hot_board

data class HotBoardsItem(
val title: String = "",
val boardName: String = "",
val subtitle: String = "",
val online: String = "",
val onlineColor: String = ""
Expand Down
30 changes: 30 additions & 0 deletions app/src/main/java/tw/y_studio/ptt/di/ApiModules.kt
Original file line number Diff line number Diff line change
@@ -1,12 +1,42 @@
package tw.y_studio.ptt.di

import okhttp3.OkHttpClient
import org.koin.dsl.module
import retrofit2.Retrofit
import retrofit2.converter.gson.GsonConverterFactory
import tw.y_studio.ptt.BuildConfig
import tw.y_studio.ptt.api.PopularBoardListAPI
import tw.y_studio.ptt.api.PostAPI
import tw.y_studio.ptt.api.SearchBoardAPI
import tw.y_studio.ptt.api.board.BoardApiService
import tw.y_studio.ptt.utils.OkHttpUtils
import java.util.concurrent.TimeUnit

val apiModules = module {
factory { PopularBoardListAPI() }
factory { SearchBoardAPI() }
factory { PostAPI() }
single { provideOkHttpClient() }
single { provideRetrofit(get()) }
factory { provideBoardApiService(get()) }
}

private fun provideRetrofit(client: OkHttpClient): Retrofit {
return Retrofit.Builder()
.baseUrl(BuildConfig.develop_domain)
.client(client)
.addConverterFactory(GsonConverterFactory.create())
.build()
}

private fun provideOkHttpClient(): OkHttpClient {
return OkHttpClient.Builder().connectTimeout(30, TimeUnit.SECONDS)
.writeTimeout(30, TimeUnit.SECONDS)
.readTimeout(30, TimeUnit.SECONDS)
.addInterceptor(OkHttpUtils.GzipRequestInterceptor()) // TODO: 2021/1/31 add TokenInterceptor
.build()
}

private fun provideBoardApiService(retrofit: Retrofit): BoardApiService {
return retrofit.create(BoardApiService::class.java)
}
6 changes: 3 additions & 3 deletions app/src/main/java/tw/y_studio/ptt/di/DataSourceModules.kt
Original file line number Diff line number Diff line change
@@ -1,15 +1,15 @@
package tw.y_studio.ptt.di

import org.koin.dsl.module
import tw.y_studio.ptt.source.remote.popular.IPopularRemoteDataSource
import tw.y_studio.ptt.source.remote.popular.PopularRemoteDataSourceImpl
import tw.y_studio.ptt.source.remote.board.IPopularRemoteDataSource
import tw.y_studio.ptt.source.remote.board.PopularRemoteDataSourceImpl
import tw.y_studio.ptt.source.remote.post.IPostRemoteDataSource
import tw.y_studio.ptt.source.remote.post.PostRemoteDataSourceImpl
import tw.y_studio.ptt.source.remote.search.ISearchBoardRemoteDataSource
import tw.y_studio.ptt.source.remote.search.SearchBoardRemoteDataSourceImpl

val dataSourceModules = module {
factory<IPopularRemoteDataSource> { PopularRemoteDataSourceImpl(get()) }
factory<IPopularRemoteDataSource> { PopularRemoteDataSourceImpl(get(), get()) }
factory<ISearchBoardRemoteDataSource> { SearchBoardRemoteDataSourceImpl(get()) }
factory<IPostRemoteDataSource> { PostRemoteDataSourceImpl(get()) }
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
package tw.y_studio.ptt.source.remote.board

import tw.y_studio.ptt.api.model.hot_board.HotBoard
import tw.y_studio.ptt.api.model.hot_board.HotBoardTemp

interface IPopularRemoteDataSource {

fun getPopularBoardData(page: Int, count: Int): MutableList<HotBoardTemp>

suspend fun getPopularBoards(): HotBoard

fun disposeAll()
}
Original file line number Diff line number Diff line change
@@ -1,17 +1,24 @@
package tw.y_studio.ptt.source.remote.popular
package tw.y_studio.ptt.source.remote.board

import tw.y_studio.ptt.api.PopularBoardListAPI
import tw.y_studio.ptt.model.HotBoard
import tw.y_studio.ptt.api.board.BoardApiService
import tw.y_studio.ptt.api.model.hot_board.HotBoard
import tw.y_studio.ptt.api.model.hot_board.HotBoardTemp

class PopularRemoteDataSourceImpl(
private val boardApiService: BoardApiService,
private val popularBoardListAPI: PopularBoardListAPI
) : IPopularRemoteDataSource {

@Throws(Exception::class)
override fun getPopularBoardData(page: Int, count: Int): MutableList<HotBoard> {
override fun getPopularBoardData(page: Int, count: Int): MutableList<HotBoardTemp> {
return popularBoardListAPI.refresh(page, count)
}

override suspend fun getPopularBoards(): HotBoard {
return boardApiService.getPopularBoard()
}

override fun disposeAll() {
popularBoardListAPI.close()
}
Expand Down

This file was deleted.

Original file line number Diff line number Diff line change
@@ -1,9 +1,9 @@
package tw.y_studio.ptt.source.remote.post

import tw.y_studio.ptt.api.PostRankMark
import tw.y_studio.ptt.model.PartialPost
import tw.y_studio.ptt.model.Post
import tw.y_studio.ptt.model.PostRank
import tw.y_studio.ptt.api.model.PartialPost
import tw.y_studio.ptt.api.model.Post
import tw.y_studio.ptt.api.model.PostRank

interface IPostRemoteDataSource {
fun getPost(board: String, fileName: String): Post
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -2,9 +2,9 @@ package tw.y_studio.ptt.source.remote.post

import tw.y_studio.ptt.api.PostAPI
import tw.y_studio.ptt.api.PostRankMark
import tw.y_studio.ptt.model.PartialPost
import tw.y_studio.ptt.model.Post
import tw.y_studio.ptt.model.PostRank
import tw.y_studio.ptt.api.model.PartialPost
import tw.y_studio.ptt.api.model.Post
import tw.y_studio.ptt.api.model.PostRank

class PostRemoteDataSourceImpl(
private val postAPI: PostAPI
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -3,9 +3,9 @@ package tw.y_studio.ptt.ui.article.list
import android.view.LayoutInflater
import android.view.ViewGroup
import androidx.recyclerview.widget.RecyclerView
import tw.y_studio.ptt.api.model.PartialPost
import tw.y_studio.ptt.databinding.ArticleListItemBinding
import tw.y_studio.ptt.databinding.ArticleListItemDeleteBinding
import tw.y_studio.ptt.model.PartialPost

class ArticleListAdapter(
private val partialPostList: List<PartialPost>,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -9,10 +9,10 @@ import androidx.recyclerview.widget.RecyclerView
import com.google.android.material.bottomnavigation.BottomNavigationView
import org.koin.androidx.viewmodel.ext.android.viewModel
import tw.y_studio.ptt.R
import tw.y_studio.ptt.api.model.PartialPost
import tw.y_studio.ptt.databinding.ArticleListFragmentLayoutBinding
import tw.y_studio.ptt.fragment.ArticleListSearchFragment
import tw.y_studio.ptt.fragment.PostArticleFragment
import tw.y_studio.ptt.model.PartialPost
import tw.y_studio.ptt.ui.BaseFragment
import tw.y_studio.ptt.ui.ClickFix
import tw.y_studio.ptt.ui.CustomLinearLayoutManager
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@ import androidx.lifecycle.viewModelScope
import kotlinx.coroutines.CoroutineDispatcher
import kotlinx.coroutines.launch
import kotlinx.coroutines.withContext
import tw.y_studio.ptt.model.PartialPost
import tw.y_studio.ptt.api.model.PartialPost
import tw.y_studio.ptt.source.remote.post.IPostRemoteDataSource
import tw.y_studio.ptt.utils.Log
import java.util.*
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -2,8 +2,8 @@ package tw.y_studio.ptt.ui.article.list

import androidx.recyclerview.widget.RecyclerView
import tw.y_studio.ptt.R
import tw.y_studio.ptt.api.model.PartialPost
import tw.y_studio.ptt.databinding.ArticleListItemDeleteBinding
import tw.y_studio.ptt.model.PartialPost
import tw.y_studio.ptt.utils.ResourcesUtils

class DeletedViewHolder(private val binding: ArticleListItemDeleteBinding) : RecyclerView.ViewHolder(binding.root) {
Expand Down
Loading

0 comments on commit 15a0094

Please sign in to comment.