Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Feat : 설정화면 fcm 토큰 관련 api 연동 #216

Merged
merged 7 commits into from
Mar 31, 2024
Original file line number Diff line number Diff line change
Expand Up @@ -37,16 +37,24 @@ object SharedPreference {
// 최초 접속 여부
private const val FIRST_LAUNCH = "FIRST_LAUNCH"
fun getIsFirstLaunch(): Boolean = pref?.getBoolean(FIRST_LAUNCH, true) ?: true
fun setIsFirstLaunch(isFirstLaunch: Boolean) = pref?.edit()?.putBoolean(FIRST_LAUNCH, isFirstLaunch)?.apply()
fun setIsFirstLaunch(isFirstLaunch: Boolean) =
pref?.edit()?.putBoolean(FIRST_LAUNCH, isFirstLaunch)?.apply()

// 학교 알림 설정 여부
private const val ACCESS_SCHOOL_ALARM = "ACCESS_SCHOOL_ALARM"
fun getIsAccessSchoolAlarm(): Boolean = pref?.getBoolean(ACCESS_SCHOOL_ALARM, true) ?: true
fun setIsAccessSchoolAlarm(isAccessSchoolAlarm: Boolean) = pref?.edit()?.putBoolean(ACCESS_SCHOOL_ALARM, isAccessSchoolAlarm)?.apply()
fun setIsAccessSchoolAlarm(isAccessSchoolAlarm: Boolean) =
pref?.edit()?.putBoolean(ACCESS_SCHOOL_ALARM, isAccessSchoolAlarm)?.apply()

// 학과 알림 설정 여부
private const val ACCESS_DEPART_ALARM = "ACCESS_DEPART_ALARM"
fun getIsAccessDepartAlarm(): Boolean = pref?.getBoolean(ACCESS_DEPART_ALARM, true) ?: true
fun setIsAccessDepartAlarm(isAccessDepartAlarm: Boolean) = pref?.edit()?.putBoolean(ACCESS_DEPART_ALARM, isAccessDepartAlarm)?.apply()
fun setIsAccessDepartAlarm(isAccessDepartAlarm: Boolean) =
pref?.edit()?.putBoolean(ACCESS_DEPART_ALARM, isAccessDepartAlarm)?.apply()

// FCM 토큰
private const val FCM_TOKEN = "NO_TOKEN"
fun getFCMToken(): String = pref?.getString(FCM_TOKEN, "0") ?: "0"
fun setFcmToken(token: String) = pref?.edit()?.putString(FCM_TOKEN, token)?.apply()

}
Original file line number Diff line number Diff line change
Expand Up @@ -23,4 +23,7 @@ interface KeywordDao {

@Query("DELETE FROM keyword WHERE name = :name")
suspend fun deleteKeyword(name: String)

@Query("SELECT * FROM keyword WHERE isSubscribe = 1")
suspend fun getSubscribedKeywords(): List<KeywordEntity>
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
package com.dongyang.android.youdongknowme.data.remote.entity

data class UpdateDepartment(
val token: String,
val department: String,
)

data class RemoveToken(
val token: String,
)

data class UpdateTopic(
val token: String,
val topics: List<String>,
)
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
package com.dongyang.android.youdongknowme.data.remote.service

import com.dongyang.android.youdongknowme.data.remote.entity.RemoveToken
import com.dongyang.android.youdongknowme.data.remote.entity.UpdateDepartment
import com.dongyang.android.youdongknowme.data.remote.entity.UpdateTopic
import retrofit2.http.Body
import retrofit2.http.POST

interface SettingService {

@POST("department/v1/dmu/updateDepartment")
suspend fun updateDepartment(@Body data: UpdateDepartment)

@POST("department/v1/dmu/deleteDepartment")
suspend fun deleteDepartment(@Body token: RemoveToken)

@POST("token/v1/dmu/updateTopic")
suspend fun updateTopic(@Body data: UpdateTopic)

@POST("token/v1/dmu/deleteTopic")
suspend fun deleteTopic(@Body token: RemoveToken)
}
Original file line number Diff line number Diff line change
@@ -1,10 +1,21 @@
package com.dongyang.android.youdongknowme.data.repository

import com.dongyang.android.youdongknowme.data.local.SharedPreference
import com.dongyang.android.youdongknowme.data.local.dao.KeywordDao
import com.dongyang.android.youdongknowme.data.remote.entity.RemoveToken
import com.dongyang.android.youdongknowme.data.remote.entity.UpdateDepartment
import com.dongyang.android.youdongknowme.data.remote.entity.UpdateTopic
import com.dongyang.android.youdongknowme.data.remote.service.SettingService
import com.dongyang.android.youdongknowme.standard.network.ErrorResponseHandler
import com.dongyang.android.youdongknowme.standard.network.NetworkResult
import com.dongyang.android.youdongknowme.standard.network.RetrofitObject

class SettingRepository {
class SettingRepository(
private val keywordDao: KeywordDao,
private val errorResponseHandler: ErrorResponseHandler
) {

fun getIsAccessSchoolAlarm(): Boolean = SharedPreference.getIsAccessSchoolAlarm()
fun getIsAccessUniversityAlarm(): Boolean = SharedPreference.getIsAccessSchoolAlarm()

fun getIsAccessDepartAlarm(): Boolean = SharedPreference.getIsAccessDepartAlarm()

Expand All @@ -19,4 +30,65 @@ class SettingRepository {
fun getUserDepartment(): String {
return SharedPreference.getDepartment()
}

suspend fun getUserTopic(): List<String> {
val subscribedTopic = keywordDao.getSubscribedKeywords()
return subscribedTopic.map { it.englishName }
}

fun getUserFCMToken(): String {
return SharedPreference.getFCMToken()
}

suspend fun updateUserDepartment(
data: UpdateDepartment
): NetworkResult<Unit> {
return try {
val response = RetrofitObject.getNetwork().create(SettingService::class.java)
.updateDepartment(data)
NetworkResult.Success(response)
} catch (exception: Exception) {
val error = errorResponseHandler.getError(exception)
NetworkResult.Error(error)
}
}

suspend fun removeUserDepartment(
token: RemoveToken
): NetworkResult<Unit> {
return try {
val response = RetrofitObject.getNetwork().create(SettingService::class.java)
.deleteDepartment(token)
NetworkResult.Success(response)
} catch (exception: Exception) {
val error = errorResponseHandler.getError(exception)
NetworkResult.Error(error)
}
}

suspend fun updateUserTopic(
data: UpdateTopic
): NetworkResult<Unit> {
return try {
val response = RetrofitObject.getNetwork().create(SettingService::class.java)
.updateTopic(data)
NetworkResult.Success(response)
} catch (exception: Exception) {
val error = errorResponseHandler.getError(exception)
NetworkResult.Error(error)
}
}

suspend fun removeUserTopic(
token: RemoveToken
): NetworkResult<Unit> {
return try {
val response = RetrofitObject.getNetwork().create(SettingService::class.java)
.deleteTopic(token)
NetworkResult.Success(response)
} catch (exception: Exception) {
val error = errorResponseHandler.getError(exception)
NetworkResult.Error(error)
}
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@ import android.content.Intent
import android.media.RingtoneManager
import android.os.Build
import androidx.core.app.NotificationCompat
import com.dongyang.android.youdongknowme.data.local.SharedPreference
import com.dongyang.android.youdongknowme.ui.view.main.MainActivity
import com.google.firebase.messaging.FirebaseMessagingService
import com.google.firebase.messaging.RemoteMessage
Expand Down Expand Up @@ -59,4 +60,9 @@ class FCMService : FirebaseMessagingService() {
// 알림 표시
notificationManager.notify(System.currentTimeMillis().toInt(), builder.build())
}

override fun onNewToken(token: String) {
super.onNewToken(token)
SharedPreference.setFcmToken(token)
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -117,7 +117,7 @@ val repositoryModule = module {
KeywordRepository(get())
}
single {
SettingRepository()
SettingRepository(get(), get())
}
single {
AlarmRepository(get())
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@ import retrofit2.converter.gson.GsonConverterFactory
import java.util.concurrent.TimeUnit

object RetrofitObject {
private const val TIME_OUT_COUNT: Long = 10
private const val TIME_OUT_COUNT: Long = 30

Comment on lines 11 to 13
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

네트워크 시간 때문에 늘린건가요?

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

넵 키워드 때문에 타임 아웃 에러나서 서버 측에서 로직 수정해주시면 다시 10으로 되돌릴 예정입니당

fun getNetwork(): Retrofit {
val baseInterceptor = Interceptor { chain ->
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -64,9 +64,6 @@ class DepartActivity : BaseActivity<ActivityDepartBinding, DepartViewModel>(), D
private fun getDepart(items: ArrayList<String>) {
return binding.btnDepartComplete.setOnClickListener {
viewModel.setDepartment(items[viewModel.selectDepartPosition.value ?: 0])
val intent = Intent(this, MainActivity::class.java)
intent.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP)
startActivity(intent)
finish()
Comment on lines 66 to 67
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

메인 화면으로 이동하는 부분은 일부러 지우신건가요?

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

네 이 부분 사용해보셨는지 모르겠는데 불편하기도 하고, 학과가 바꼈는지 확인이 안 되기에 finish처리만 했습니다.

}
}
Expand Down
Original file line number Diff line number Diff line change
@@ -1,12 +1,10 @@
package com.dongyang.android.youdongknowme.ui.view.keyword

import android.content.Intent
import androidx.lifecycle.Observer
import com.dongyang.android.youdongknowme.R
import com.dongyang.android.youdongknowme.data.local.entity.KeywordEntity
import com.dongyang.android.youdongknowme.databinding.ActivityKeywordBinding
import com.dongyang.android.youdongknowme.standard.base.BaseActivity
import com.dongyang.android.youdongknowme.ui.view.permission.OnboardingPermissionActivity
import com.google.android.material.chip.Chip
import com.google.android.material.chip.ChipGroup
import org.koin.androidx.viewmodel.ext.android.viewModel
Expand All @@ -17,7 +15,7 @@ class KeywordActivity : BaseActivity<ActivityKeywordBinding, KeywordViewModel>()
override val viewModel: KeywordViewModel by viewModel()

override fun initStartView() = Unit

override fun initDataBinding() {
// 효율을 위해 단 한번만 옵저빙하여 이미 구독중인 항목을 선택 처리
viewModel.localKeywordList.observe(this, object : Observer<List<KeywordEntity>> {
Expand All @@ -40,14 +38,9 @@ class KeywordActivity : BaseActivity<ActivityKeywordBinding, KeywordViewModel>()
viewModel.checkFirstLaunch()
viewModel.getLocalKeywordList()

// TODO :: 안드로이드 데이터베이스에 유저별 설정한 키워드 저장 및 파이어베이스 키워드 구독 설정
binding.btnKeywordComplete.setOnClickListener {
viewModel.subscribeCheckedKeyword()
if (viewModel.isFirstLaunch.value == true) {
viewModel.setFirstLaunch(false)
val intent = Intent(this@KeywordActivity, OnboardingPermissionActivity::class.java)
startActivity(intent)
}
Comment on lines -46 to -50
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

👍

setResult(RESULT_OK)
finish()
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -6,13 +6,13 @@ import androidx.navigation.fragment.NavHostFragment
import androidx.navigation.plusAssign
import androidx.navigation.ui.setupWithNavController
import com.dongyang.android.youdongknowme.R
import com.dongyang.android.youdongknowme.data.local.SharedPreference
import com.dongyang.android.youdongknowme.databinding.ActivityMainBinding
import com.dongyang.android.youdongknowme.standard.base.BaseActivity
import com.dongyang.android.youdongknowme.ui.view.util.KeepStateNavigator
import com.google.android.gms.tasks.OnCompleteListener
import com.google.firebase.messaging.FirebaseMessaging
import org.koin.androidx.viewmodel.ext.android.viewModel
import timber.log.Timber

/* 메인 액티비티 */
class MainActivity : BaseActivity<ActivityMainBinding, MainViewModel>() {
Expand All @@ -38,9 +38,9 @@ class MainActivity : BaseActivity<ActivityMainBinding, MainViewModel>() {
getFcmToken()
}

override fun initDataBinding() {}
override fun initDataBinding() = Unit

override fun initAfterBinding() {}
override fun initAfterBinding() = Unit

private fun getFcmToken() {
FirebaseMessaging.getInstance().token.addOnCompleteListener(OnCompleteListener { task ->
Expand All @@ -49,9 +49,7 @@ class MainActivity : BaseActivity<ActivityMainBinding, MainViewModel>() {
}

val token = task.result
Timber.d(token)
//TODO: prefs 선언 중복 제거될 경우 주석 제거
//prefs.edit().putString("fcm_token", token).commit()
SharedPreference.setFcmToken(token)
})
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -75,7 +75,7 @@ class OnboardingPermissionActivity :
binding.mvSwitchPermission.strokeColor = getColor(resources)

binding.switchPermission.isChecked = isChecked
viewModel.setIsAccessSchoolAlarm(isChecked)
viewModel.setIsAccessUniversityAlarm(isChecked)
viewModel.setIsAccessDepartAlarm(isChecked)
}
}
Original file line number Diff line number Diff line change
@@ -1,7 +1,10 @@
package com.dongyang.android.youdongknowme.ui.view.setting

import android.app.Activity
import android.content.Intent
import android.net.Uri
import androidx.activity.result.ActivityResultLauncher
import androidx.activity.result.contract.ActivityResultContracts
import com.dongyang.android.youdongknowme.R
import com.dongyang.android.youdongknowme.databinding.FragmentSettingBinding
import com.dongyang.android.youdongknowme.standard.base.BaseFragment
Expand All @@ -16,13 +19,22 @@ class SettingFragment : BaseFragment<FragmentSettingBinding, SettingViewModel>()
override val layoutResourceId: Int = R.layout.fragment_setting
override val viewModel: SettingViewModel by viewModel()

private lateinit var resultLauncher: ActivityResultLauncher<Intent>
private var topics: List<String> = emptyList()

override fun initStartView() {
binding.tvSettingAppVersion.text = getAppVersion()
setResultKeyword()
}
Comment on lines +24 to 28
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

첫 줄 함수 개행으로 컨벤션 확정인가요?
전에 같은 이슈가 나왔었는데 확실하게 정하지 못했던거 같아서 여쭤봅니다!

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

넴 고고 합시다


override fun initDataBinding() {
viewModel.myDepartment.observe(viewLifecycleOwner) { department ->
binding.tvSettingDepartment.text = department

viewModel.myDepartment.observe(viewLifecycleOwner) { myDepartment ->
binding.tvSettingDepartment.text = myDepartment
}

viewModel.myTopics.observe(viewLifecycleOwner) { myTopics ->
topics = topics
}

viewModel.isAccessUniversityAlarm.observe(viewLifecycleOwner) { isChecked ->
Expand All @@ -35,28 +47,30 @@ class SettingFragment : BaseFragment<FragmentSettingBinding, SettingViewModel>()
}

override fun initAfterBinding() {

viewModel.checkAccessAlarm()
viewModel.getUserDepartment()
viewModel.getUserTopic()

binding.switchSettingUniversityAlarm.setOnCheckedChangeListener { compoundButton, _ ->
if (compoundButton.isChecked) {
viewModel.setIsAccessSchoolAlarm(true)
viewModel.updateUserTopic(topics)
} else {
viewModel.setIsAccessSchoolAlarm(false)
viewModel.removeUserTopic()
}
}

binding.switchSettingDepartmentAlarm.setOnCheckedChangeListener { compoundButton, _ ->
if (compoundButton.isChecked) {
viewModel.setIsAccessDepartAlarm(true)
viewModel.updateUserDepartment()
} else {
viewModel.setIsAccessDepartAlarm(false)
viewModel.removeUserDepartment()
}
}

binding.btnSettingEditKeyword.setOnClickListener {
val intent = Intent(requireActivity(), KeywordActivity::class.java)
startActivity(intent)
resultLauncher.launch(intent)
}

binding.btnSettingEditDepartment.setOnClickListener {
Expand Down Expand Up @@ -92,4 +106,14 @@ class SettingFragment : BaseFragment<FragmentSettingBinding, SettingViewModel>()
requireContext().packageManager.getPackageInfo(requireContext().packageName, 0)
return packageManager.versionName
}

private fun setResultKeyword() {
resultLauncher =
registerForActivityResult(ActivityResultContracts.StartActivityForResult()) { result ->
if (result.resultCode == Activity.RESULT_OK) {
viewModel.getUserTopic()
viewModel.updateUserTopic(topics)
}
}
}
}
Loading
Loading