├── .gitignore
├── LICENSE
├── README.md
├── app
├── .gitignore
├── build.gradle.kts
├── proguard-rules.pro
└── src
│ ├── androidTest
│ └── java
│ │ └── com
│ │ └── lateinit
│ │ └── rightweight
│ │ ├── CustomTestRunner.kt
│ │ ├── ExampleInstrumentedTest.kt
│ │ └── SharedRoutineTest.kt
│ ├── main
│ ├── AndroidManifest.xml
│ ├── java
│ │ └── com
│ │ │ └── lateinit
│ │ │ └── rightweight
│ │ │ ├── RightWeightApplication.kt
│ │ │ ├── data
│ │ │ ├── api
│ │ │ │ ├── AuthApiService.kt
│ │ │ │ ├── RoutineApiService.kt
│ │ │ │ └── UserApiService.kt
│ │ │ ├── dataStore
│ │ │ │ └── AppPreferencesDataStore.kt
│ │ │ ├── database
│ │ │ │ ├── AppDatabase.kt
│ │ │ │ ├── Converters.kt
│ │ │ │ ├── dao
│ │ │ │ │ ├── HistoryDao.kt
│ │ │ │ │ ├── RoutineDao.kt
│ │ │ │ │ └── SharedRoutineDao.kt
│ │ │ │ ├── entity
│ │ │ │ │ ├── Day.kt
│ │ │ │ │ ├── Exercise.kt
│ │ │ │ │ ├── ExerciseSet.kt
│ │ │ │ │ ├── History.kt
│ │ │ │ │ ├── HistoryExercise.kt
│ │ │ │ │ ├── HistorySet.kt
│ │ │ │ │ ├── Routine.kt
│ │ │ │ │ ├── SharedRoutine.kt
│ │ │ │ │ ├── SharedRoutineDay.kt
│ │ │ │ │ ├── SharedRoutineExercise.kt
│ │ │ │ │ └── SharedRoutineExerciseSet.kt
│ │ │ │ └── intermediate
│ │ │ │ │ ├── DayWithExercises.kt
│ │ │ │ │ ├── ExerciseWithSets.kt
│ │ │ │ │ ├── HistoryExerciseWithHistorySets.kt
│ │ │ │ │ ├── HistoryWithHistoryExercises.kt
│ │ │ │ │ ├── RoutineWithDays.kt
│ │ │ │ │ ├── SharedRoutineDayWithExercises.kt
│ │ │ │ │ ├── SharedRoutineExerciseWithExerciseSets.kt
│ │ │ │ │ └── SharedRoutineWithDays.kt
│ │ │ ├── datasource
│ │ │ │ ├── local
│ │ │ │ │ ├── HistoryLocalDataSource.kt
│ │ │ │ │ ├── RoutineLocalDataSource.kt
│ │ │ │ │ ├── SharedRoutineLocalDataSource.kt
│ │ │ │ │ ├── UserLocalDataSource.kt
│ │ │ │ │ └── impl
│ │ │ │ │ │ ├── HistoryLocalDataSourceImpl.kt
│ │ │ │ │ │ ├── RoutineLocalDataSourceImpl.kt
│ │ │ │ │ │ ├── SharedRoutineLocalDataSourceImpl.kt
│ │ │ │ │ │ └── UserLocalDataSourceImpl.kt
│ │ │ │ └── remote
│ │ │ │ │ ├── HistoryRemoteDatasource.kt
│ │ │ │ │ ├── LoginDataSource.kt
│ │ │ │ │ ├── RoutineRemoteDataSource.kt
│ │ │ │ │ ├── SharedRoutineRemoteDataSource.kt
│ │ │ │ │ ├── UserRemoteDataSource.kt
│ │ │ │ │ └── impl
│ │ │ │ │ ├── HistoryRemoteDataSourceImpl.kt
│ │ │ │ │ ├── LoginDataSourceImpl.kt
│ │ │ │ │ ├── RoutineRemoteDataSourceImpl.kt
│ │ │ │ │ ├── SharedRoutineRemoteDataSourceImpl.kt
│ │ │ │ │ └── UserRemoteDataSourceImpl.kt
│ │ │ ├── mapper
│ │ │ │ ├── local
│ │ │ │ │ ├── ToExercisePartType.kt
│ │ │ │ │ ├── ToHistory.kt
│ │ │ │ │ ├── ToRoutine.kt
│ │ │ │ │ ├── ToSharedRoutine.kt
│ │ │ │ │ └── ToSharedRoutineSortType.kt
│ │ │ │ └── remote
│ │ │ │ │ ├── ToHisttoryField.kt
│ │ │ │ │ ├── ToRoutineField.kt
│ │ │ │ │ └── ToSharedRoutineField.kt
│ │ │ ├── mediator
│ │ │ │ └── SharedRoutineRemoteMediator.kt
│ │ │ ├── model
│ │ │ │ ├── local
│ │ │ │ │ ├── ExercisePartType.kt
│ │ │ │ │ └── User.kt
│ │ │ │ └── remote
│ │ │ │ │ ├── DataValue.kt
│ │ │ │ │ ├── Documents.kt
│ │ │ │ │ ├── LoginModel.kt
│ │ │ │ │ ├── LoginResponse.kt
│ │ │ │ │ ├── RemoteData.kt
│ │ │ │ │ ├── RootField.kt
│ │ │ │ │ ├── RunQueryModel.kt
│ │ │ │ │ └── WriteModel.kt
│ │ │ └── repository
│ │ │ │ ├── HistoryRepository.kt
│ │ │ │ ├── LoginRepository.kt
│ │ │ │ ├── RoutineRepository.kt
│ │ │ │ ├── SharedRoutineRepository.kt
│ │ │ │ ├── UserRepository.kt
│ │ │ │ └── impl
│ │ │ │ ├── HistoryRepositoryImpl.kt
│ │ │ │ ├── LoginRepositoryImpl.kt
│ │ │ │ ├── RoutineRepositoryImpl.kt
│ │ │ │ ├── SharedRoutineRepositoryImpl.kt
│ │ │ │ └── UserRepositoryImpl.kt
│ │ │ ├── di
│ │ │ ├── ApiModule.kt
│ │ │ ├── DataSourceModule.kt
│ │ │ ├── DatabaseModule.kt
│ │ │ └── RepositoryModule.kt
│ │ │ ├── service
│ │ │ └── TimerService.kt
│ │ │ ├── ui
│ │ │ ├── MainActivity.kt
│ │ │ ├── MainViewModel.kt
│ │ │ ├── calendar
│ │ │ │ ├── CalendarFragment.kt
│ │ │ │ ├── CalendarViewModel.kt
│ │ │ │ ├── CompletedDayDecorator.kt
│ │ │ │ └── DayDecorator.kt
│ │ │ ├── dialog
│ │ │ │ ├── CommonDialogFragment.kt
│ │ │ │ └── LoadingDialog.kt
│ │ │ ├── exercise
│ │ │ │ ├── ExerciseFragment.kt
│ │ │ │ ├── ExerciseViewModel.kt
│ │ │ │ ├── HistoryEventListener.kt
│ │ │ │ ├── HistoryExerciseAdapter.kt
│ │ │ │ └── HistorySetAdapter.kt
│ │ │ ├── home
│ │ │ │ ├── ExpandableItemAnimator.kt
│ │ │ │ ├── HomeAdapter.kt
│ │ │ │ ├── HomeBindingAdapter.kt
│ │ │ │ ├── HomeFragment.kt
│ │ │ │ └── HomeViewModel.kt
│ │ │ ├── login
│ │ │ │ ├── LoginActivity.kt
│ │ │ │ └── LoginViewModel.kt
│ │ │ ├── mapper
│ │ │ │ ├── ExercisePartType.kt
│ │ │ │ ├── HistoryUiModel.kt
│ │ │ │ ├── Routine.kt
│ │ │ │ └── SharedRoutine.kt
│ │ │ ├── model
│ │ │ │ ├── LoadingState.kt
│ │ │ │ ├── ParentDayUiModel.kt
│ │ │ │ ├── ParentExerciseSetUiModel.kt
│ │ │ │ ├── ParentExerciseUiModel.kt
│ │ │ │ ├── ParentRoutineUiModel.kt
│ │ │ │ ├── history
│ │ │ │ │ ├── HistoryExerciseSetUiModel.kt
│ │ │ │ │ ├── HistoryExerciseUiModel.kt
│ │ │ │ │ └── HistoryUiModel.kt
│ │ │ │ ├── routine
│ │ │ │ │ ├── DayUiModel.kt
│ │ │ │ │ ├── ExercisePartTypeUiModel.kt
│ │ │ │ │ ├── ExerciseSetUiModel.kt
│ │ │ │ │ ├── ExerciseUiModel.kt
│ │ │ │ │ └── RoutineUiModel.kt
│ │ │ │ └── shared
│ │ │ │ │ ├── SharedRoutineSortTypeUiModel.kt
│ │ │ │ │ └── SharedRoutineUiModel.kt
│ │ │ ├── routine
│ │ │ │ ├── detail
│ │ │ │ │ ├── DetailExerciseAdapter.kt
│ │ │ │ │ ├── DetailExerciseSetAdapter.kt
│ │ │ │ │ ├── RoutineDetailFragment.kt
│ │ │ │ │ └── RoutineDetailViewModel.kt
│ │ │ │ ├── editor
│ │ │ │ │ ├── RoutineDayAdapter.kt
│ │ │ │ │ ├── RoutineEditorFragment.kt
│ │ │ │ │ ├── RoutineEditorViewModel.kt
│ │ │ │ │ ├── RoutineExerciseAdapter.kt
│ │ │ │ │ └── RoutineSetAdapter.kt
│ │ │ │ └── management
│ │ │ │ │ ├── RoutineAdapter.kt
│ │ │ │ │ ├── RoutineManagementFragment.kt
│ │ │ │ │ └── RoutineManagementViewModel.kt
│ │ │ └── share
│ │ │ │ ├── SharedRoutineClickHandler.kt
│ │ │ │ ├── SharedRoutineFragment.kt
│ │ │ │ ├── SharedRoutinePagingAdapter.kt
│ │ │ │ ├── SharedRoutineViewModel.kt
│ │ │ │ └── detail
│ │ │ │ ├── SharedRoutineDetailFragment.kt
│ │ │ │ └── SharedRoutineDetailViewModel.kt
│ │ │ └── util
│ │ │ ├── CenterSmoothScroller.kt
│ │ │ ├── Consts.kt
│ │ │ ├── Extensions.kt
│ │ │ ├── TimeConverter.kt
│ │ │ └── UUID.kt
│ └── res
│ │ ├── color
│ │ ├── color_completed_day_background.xml
│ │ ├── color_day_background.xml
│ │ └── color_day_text.xml
│ │ ├── drawable-v24
│ │ └── ic_launcher_foreground.xml
│ │ ├── drawable
│ │ ├── bg_calendar_day.xml
│ │ ├── bg_calendar_day_completed.xml
│ │ ├── bg_day_order.xml
│ │ ├── bg_day_order_selected.xml
│ │ ├── bg_exercise_part.xml
│ │ ├── ic_add.xml
│ │ ├── ic_arrow_down.xml
│ │ ├── ic_arrow_up.xml
│ │ ├── ic_back.xml
│ │ ├── ic_backup.xml
│ │ ├── ic_calendar.xml
│ │ ├── ic_down_arrow.xml
│ │ ├── ic_download.xml
│ │ ├── ic_home.xml
│ │ ├── ic_launcher_background.xml
│ │ ├── ic_logout.xml
│ │ ├── ic_more.xml
│ │ ├── ic_pause.xml
│ │ ├── ic_play_arrow.xml
│ │ ├── ic_remove.xml
│ │ ├── ic_routine_management.xml
│ │ ├── ic_shared_routine.xml
│ │ ├── ic_splash_logo.xml
│ │ ├── ic_up_arrow.xml
│ │ ├── ic_withdraw.xml
│ │ ├── img_completed.xml
│ │ └── img_right_weight.xml
│ │ ├── layout
│ │ ├── activity_login.xml
│ │ ├── activity_main.xml
│ │ ├── dialog_loading.xml
│ │ ├── fragment_calendar.xml
│ │ ├── fragment_exercise.xml
│ │ ├── fragment_home.xml
│ │ ├── fragment_routine_detail.xml
│ │ ├── fragment_routine_editor.xml
│ │ ├── fragment_routine_management.xml
│ │ ├── fragment_shared_routine.xml
│ │ ├── fragment_shared_routine_detail.xml
│ │ ├── item_day.xml
│ │ ├── item_exercise.xml
│ │ ├── item_exercise_part.xml
│ │ ├── item_exercise_view_home.xml
│ │ ├── item_exercise_with_sets.xml
│ │ ├── item_history_set.xml
│ │ ├── item_routine.xml
│ │ ├── item_set.xml
│ │ ├── item_set_read.xml
│ │ ├── item_shared_routine.xml
│ │ ├── item_shared_routine_sort_type.xml
│ │ ├── layout_day_exercises.xml
│ │ ├── navigation_header.xml
│ │ └── notification_foreground.xml
│ │ ├── menu
│ │ ├── menu_bottom_navigation.xml
│ │ ├── menu_navigation_drawer.xml
│ │ └── menu_routine_detail.xml
│ │ ├── mipmap-anydpi-v26
│ │ ├── ic_launcher.xml
│ │ └── ic_launcher_round.xml
│ │ ├── mipmap-hdpi
│ │ ├── ic_launcher.webp
│ │ └── ic_launcher_round.webp
│ │ ├── mipmap-mdpi
│ │ ├── ic_launcher.webp
│ │ └── ic_launcher_round.webp
│ │ ├── mipmap-xhdpi
│ │ ├── ic_launcher.webp
│ │ └── ic_launcher_round.webp
│ │ ├── mipmap-xxhdpi
│ │ ├── ic_launcher.webp
│ │ └── ic_launcher_round.webp
│ │ ├── mipmap-xxxhdpi
│ │ ├── ic_launcher.webp
│ │ └── ic_launcher_round.webp
│ │ ├── navigation
│ │ └── nav_graph.xml
│ │ ├── values-night
│ │ └── themes.xml
│ │ ├── values
│ │ ├── colors.xml
│ │ ├── strings.xml
│ │ ├── styles.xml
│ │ └── themes.xml
│ │ └── xml
│ │ ├── backup_rules.xml
│ │ └── data_extraction_rules.xml
│ └── test
│ └── java
│ └── com
│ └── lateinit
│ └── rightweight
│ └── ExampleUnitTest.kt
├── build.gradle.kts
├── gradle.properties
├── gradle
└── wrapper
│ ├── gradle-wrapper.jar
│ └── gradle-wrapper.properties
├── gradlew
├── gradlew.bat
└── settings.gradle.kts
/LICENSE:
--------------------------------------------------------------------------------
1 | MIT License
2 |
3 | Copyright (c) 2022 부스트캠프 웹·모바일 7기
4 |
5 | Permission is hereby granted, free of charge, to any person obtaining a copy
6 | of this software and associated documentation files (the "Software"), to deal
7 | in the Software without restriction, including without limitation the rights
8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9 | copies of the Software, and to permit persons to whom the Software is
10 | furnished to do so, subject to the following conditions:
11 |
12 | The above copyright notice and this permission notice shall be included in all
13 | copies or substantial portions of the Software.
14 |
15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21 | SOFTWARE.
22 |
--------------------------------------------------------------------------------
/app/.gitignore:
--------------------------------------------------------------------------------
1 | /build
--------------------------------------------------------------------------------
/app/proguard-rules.pro:
--------------------------------------------------------------------------------
1 | # Add project specific ProGuard rules here.
2 | # You can control the set of applied configuration files using the
3 | # proguardFiles setting in build.gradle.kts.
4 | #
5 | # For more details, see
6 | # http://developer.android.com/guide/developing/tools/proguard.html
7 |
8 | # If your project uses WebView with JS, uncomment the following
9 | # and specify the fully qualified class name to the JavaScript interface
10 | # class:
11 | #-keepclassmembers class fqcn.of.javascript.interface.for.webview {
12 | # public *;
13 | #}
14 |
15 | # Uncomment this to preserve the line number information for
16 | # debugging stack traces.
17 | #-keepattributes SourceFile,LineNumberTable
18 |
19 | # If you keep the line number information, uncomment this to
20 | # hide the original source file name.
21 | #-renamesourcefileattribute SourceFile
--------------------------------------------------------------------------------
/app/src/androidTest/java/com/lateinit/rightweight/CustomTestRunner.kt:
--------------------------------------------------------------------------------
1 | package com.lateinit.rightweight
2 |
3 | import android.app.Application
4 | import android.content.Context
5 | import androidx.test.runner.AndroidJUnitRunner
6 | import dagger.hilt.android.testing.HiltTestApplication
7 |
8 | class CustomTestRunner : AndroidJUnitRunner() {
9 | override fun newApplication(cl: ClassLoader?, name: String?, context: Context?): Application {
10 | return super.newApplication(cl, HiltTestApplication::class.java.name, context)
11 | }
12 | }
--------------------------------------------------------------------------------
/app/src/androidTest/java/com/lateinit/rightweight/ExampleInstrumentedTest.kt:
--------------------------------------------------------------------------------
1 | package com.lateinit.rightweight
2 |
3 | import androidx.test.platform.app.InstrumentationRegistry
4 | import androidx.test.ext.junit.runners.AndroidJUnit4
5 |
6 | import org.junit.Test
7 | import org.junit.runner.RunWith
8 |
9 | import org.junit.Assert.*
10 |
11 | /**
12 | * Instrumented test, which will execute on an Android device.
13 | *
14 | * See [testing documentation](http://d.android.com/tools/testing).
15 | */
16 | @RunWith(AndroidJUnit4::class)
17 | class ExampleInstrumentedTest {
18 | @Test
19 | fun useAppContext() {
20 | // Context of the app under test.
21 | val appContext = InstrumentationRegistry.getInstrumentation().targetContext
22 | assertEquals("com.lateinit.rightweight", appContext.packageName)
23 | }
24 | }
--------------------------------------------------------------------------------
/app/src/main/AndroidManifest.xml:
--------------------------------------------------------------------------------
1 |
2 |
4 |
5 |
6 |
7 |
8 |
18 |
25 |
26 |
29 |
30 |
31 |
37 |
38 |
39 |
40 |
41 |
42 |
43 |
46 |
47 |
48 |
51 |
52 |
53 |
54 |
--------------------------------------------------------------------------------
/app/src/main/java/com/lateinit/rightweight/RightWeightApplication.kt:
--------------------------------------------------------------------------------
1 | package com.lateinit.rightweight
2 |
3 | import android.app.Application
4 | import dagger.hilt.android.HiltAndroidApp
5 |
6 | @HiltAndroidApp
7 | class RightWeightApplication : Application()
--------------------------------------------------------------------------------
/app/src/main/java/com/lateinit/rightweight/data/api/AuthApiService.kt:
--------------------------------------------------------------------------------
1 | package com.lateinit.rightweight.data.api
2 |
3 | import com.lateinit.rightweight.data.model.remote.LoginRequestBody
4 | import com.lateinit.rightweight.data.model.remote.LoginResponse
5 | import retrofit2.http.Body
6 | import retrofit2.http.Field
7 | import retrofit2.http.FormUrlEncoded
8 | import retrofit2.http.POST
9 | import retrofit2.http.Query
10 |
11 | interface AuthApiService {
12 |
13 | @POST("./accounts:signInWithIdp")
14 | suspend fun loginToFirebase(
15 | @Query("key") key: String,
16 | @Body body: LoginRequestBody,
17 | ): LoginResponse
18 |
19 | @FormUrlEncoded
20 | @POST("./accounts:delete")
21 | suspend fun deleteAccount(
22 | @Query("key") key: String,
23 | @Field("idToken") idToken: String
24 | )
25 | }
--------------------------------------------------------------------------------
/app/src/main/java/com/lateinit/rightweight/data/api/RoutineApiService.kt:
--------------------------------------------------------------------------------
1 | package com.lateinit.rightweight.data.api
2 |
3 | import com.lateinit.rightweight.data.model.remote.DetailResponse
4 | import com.lateinit.rightweight.data.model.remote.DocumentResponse
5 | import com.lateinit.rightweight.data.model.remote.DocumentsResponse
6 | import com.lateinit.rightweight.data.model.remote.RunQueryBody
7 | import com.lateinit.rightweight.data.model.remote.WriteRequestBody
8 | import com.lateinit.rightweight.data.remote.model.*
9 | import retrofit2.Response
10 | import retrofit2.http.Body
11 | import retrofit2.http.GET
12 | import retrofit2.http.POST
13 | import retrofit2.http.Path
14 |
15 | interface RoutineApiService {
16 |
17 | @POST("./documents:runQuery")
18 | suspend fun getSharedRoutines(
19 | @Body order: RunQueryBody
20 | ): List>
21 |
22 | @GET("documents/{path}")
23 | suspend fun getChildrenDocument(
24 | @Path(value = "path", encoded = true)
25 | path: String
26 | ): DocumentsResponse>
27 |
28 | @GET("documents/routine/{path}")
29 | suspend fun getRoutine(
30 | @Path("path") path: String
31 | ): DetailResponse
32 |
33 | @GET("documents/{path}")
34 | suspend fun getDays(
35 | @Path(value = "path", encoded = true)
36 | path: String
37 | ): DocumentsResponse
38 |
39 | @GET("documents/{path}")
40 | suspend fun getExercises(
41 | @Path(value = "path", encoded = true)
42 | path: String
43 | ): DocumentsResponse
44 |
45 | @GET("documents/{path}")
46 | suspend fun getExerciseSets(
47 | @Path(value = "path", encoded = true)
48 | path: String
49 | ): DocumentsResponse
50 |
51 | @GET("documents/shared_routine/{routineId}")
52 | suspend fun getSharedRoutine(
53 | @Path("routineId") routineId: String
54 | ): Response
55 |
56 | @GET("documents/shared_routine/{routineId}/day")
57 | suspend fun getSharedRoutineDays(
58 | @Path("routineId") routineId: String
59 | ): DocumentsResponse?
60 |
61 | @GET("documents/shared_routine/{routineId}/day/{dayId}/exercise")
62 | suspend fun getSharedRoutineExercises(
63 | @Path("routineId") routineId: String,
64 | @Path("dayId") dayId: String
65 | ): DocumentsResponse?
66 |
67 | @GET("documents/shared_routine/{routineId}/day/{dayId}/exercise/{exerciseId}/exercise_set")
68 | suspend fun getSharedRoutineExerciseSets(
69 | @Path("routineId") routineId: String,
70 | @Path("dayId") dayId: String,
71 | @Path("exerciseId") exerciseId: String
72 | ): DocumentsResponse?
73 |
74 | @POST("./documents:runQuery")
75 | suspend fun getUserRoutine(
76 | @Body query: RunQueryBody
77 | ): List>
78 |
79 |
80 | @POST("./documents:commit")
81 | suspend fun commitTransaction(
82 | @Body
83 | writes: WriteRequestBody
84 | )
85 |
86 | }
--------------------------------------------------------------------------------
/app/src/main/java/com/lateinit/rightweight/data/api/UserApiService.kt:
--------------------------------------------------------------------------------
1 | package com.lateinit.rightweight.data.api
2 |
3 | import com.lateinit.rightweight.data.model.remote.DetailResponse
4 | import com.lateinit.rightweight.data.model.remote.DocumentResponse
5 | import com.lateinit.rightweight.data.model.remote.DocumentsResponse
6 | import com.lateinit.rightweight.data.model.remote.RunQueryBody
7 | import com.lateinit.rightweight.data.model.remote.WriteRequestBody
8 | import com.lateinit.rightweight.data.remote.model.HistoryExerciseField
9 | import com.lateinit.rightweight.data.remote.model.HistoryExerciseSetField
10 | import com.lateinit.rightweight.data.remote.model.HistoryField
11 | import com.lateinit.rightweight.data.remote.model.RemoteData
12 | import com.lateinit.rightweight.data.remote.model.RootField
13 | import com.lateinit.rightweight.data.remote.model.UserInfoField
14 | import retrofit2.Response
15 | import retrofit2.http.Body
16 | import retrofit2.http.GET
17 | import retrofit2.http.PATCH
18 | import retrofit2.http.POST
19 | import retrofit2.http.Path
20 |
21 | interface UserApiService {
22 | @PATCH("documents/user/{userId}")
23 | suspend fun backupUserInfo(
24 | @Path("userId") userId: String,
25 | @Body userInfoField: RootField
26 | )
27 |
28 | @POST("./documents:commit")
29 | suspend fun commitTransaction(
30 | @Body
31 | writes: WriteRequestBody
32 | )
33 |
34 | @GET("documents/routine/{path}")
35 | suspend fun getChildrenDocumentName(
36 | @Path(value = "path", encoded = true)
37 | path: String
38 | ): DocumentsResponse>
39 |
40 | @POST("documents/user/{userId}/:runQuery")
41 | suspend fun getLastHistoryDate(
42 | @Path(value = "userId", encoded = true) userId: String,
43 | @Body query: RunQueryBody
44 | ): List>
45 |
46 | @GET("documents/{path}")
47 | suspend fun getHistories(
48 | @Path(value = "path", encoded = true)
49 | path: String
50 | ): DocumentsResponse
51 |
52 | @GET("documents/{path}")
53 | suspend fun getHistoryExercises(
54 | @Path(value = "path", encoded = true)
55 | path: String
56 | ): DocumentsResponse
57 |
58 | @GET("documents/{path}")
59 | suspend fun getHistoryExerciseSets(
60 | @Path(value = "path", encoded = true)
61 | path: String
62 | ): DocumentsResponse
63 |
64 | @GET("documents/user/{userId}")
65 | suspend fun restoreUserInfo(
66 | @Path(value = "userId", encoded = true) userId: String
67 | ): Response>
68 | }
--------------------------------------------------------------------------------
/app/src/main/java/com/lateinit/rightweight/data/dataStore/AppPreferencesDataStore.kt:
--------------------------------------------------------------------------------
1 | package com.lateinit.rightweight.data.dataStore
2 |
3 | import android.content.Context
4 | import androidx.datastore.core.DataStore
5 | import androidx.datastore.preferences.core.Preferences
6 | import androidx.datastore.preferences.core.edit
7 | import androidx.datastore.preferences.core.stringPreferencesKey
8 | import androidx.datastore.preferences.preferencesDataStore
9 | import com.google.gson.Gson
10 | import com.lateinit.rightweight.data.model.local.User
11 | import kotlinx.coroutines.flow.Flow
12 | import kotlinx.coroutines.flow.map
13 | import javax.inject.Inject
14 |
15 | class AppPreferencesDataStore @Inject constructor(private val context: Context) {
16 |
17 | private val Context.dataStore: DataStore by preferencesDataStore(name = "RightWeight")
18 |
19 | val userInfo: Flow = context.dataStore.data
20 | .map { preferences ->
21 | Gson().fromJson(preferences[USER_INFO], User::class.java) ?: null
22 | }
23 |
24 | val sharedRoutinePagingFlag: Flow = context.dataStore.data
25 | .map { preferences ->
26 | preferences[PAGING_FLAG] ?: ""
27 | }
28 |
29 | suspend fun saveUser(user: User) {
30 | context.dataStore.edit {
31 | it[USER_INFO] = Gson().toJson(user)
32 | }
33 | }
34 |
35 | suspend fun deleteUserInfo() {
36 | context.dataStore.edit {
37 | it.remove(USER_INFO)
38 | }
39 | }
40 |
41 | suspend fun saveSharedRoutinePagingFlag(flag: String) {
42 | context.dataStore.edit {
43 | it[PAGING_FLAG] = flag
44 | }
45 | }
46 |
47 | companion object {
48 | private val USER_INFO = stringPreferencesKey("user")
49 | private val PAGING_FLAG = stringPreferencesKey("paging_flag")
50 | }
51 | }
--------------------------------------------------------------------------------
/app/src/main/java/com/lateinit/rightweight/data/database/AppDatabase.kt:
--------------------------------------------------------------------------------
1 | package com.lateinit.rightweight.data.database
2 |
3 | import androidx.room.Database
4 | import androidx.room.RoomDatabase
5 | import androidx.room.TypeConverters
6 | import com.lateinit.rightweight.data.database.dao.HistoryDao
7 | import com.lateinit.rightweight.data.database.dao.RoutineDao
8 | import com.lateinit.rightweight.data.database.dao.SharedRoutineDao
9 | import com.lateinit.rightweight.data.database.entity.*
10 |
11 | @Database(
12 | entities = [
13 | Routine::class, Day::class, Exercise::class, ExerciseSet::class,
14 | History::class, HistoryExercise::class, HistorySet::class,
15 | SharedRoutine::class, SharedRoutineDay::class, SharedRoutineExercise::class, SharedRoutineExerciseSet::class
16 | ],
17 | version = 1,
18 | exportSchema = false
19 | )
20 | @TypeConverters(Converters::class)
21 | abstract class AppDatabase : RoomDatabase() {
22 | abstract fun routineDao(): RoutineDao
23 | abstract fun historyDao(): HistoryDao
24 | abstract fun sharedRoutineDao(): SharedRoutineDao
25 | }
--------------------------------------------------------------------------------
/app/src/main/java/com/lateinit/rightweight/data/database/Converters.kt:
--------------------------------------------------------------------------------
1 | package com.lateinit.rightweight.data.database
2 |
3 | import androidx.room.TypeConverter
4 | import java.time.*
5 |
6 | class Converters {
7 |
8 | @TypeConverter
9 | fun toLocalDateTime(timestamp: Long): LocalDateTime {
10 | return Instant.ofEpochMilli(timestamp).atZone(ZoneId.systemDefault()).toLocalDateTime()
11 | }
12 |
13 | @TypeConverter
14 | fun toTimestamp(date: LocalDateTime): Long {
15 | return date.atZone(ZoneId.systemDefault()).toInstant().toEpochMilli()
16 | }
17 |
18 | @TypeConverter
19 | fun toTimestamp(date: LocalDate): Long {
20 | return date.atTime(LocalTime.MIDNIGHT).toInstant(ZoneOffset.UTC).toEpochMilli()
21 | }
22 |
23 | @TypeConverter
24 | fun toLocalDate(timestamp: Long): LocalDate {
25 | return Instant.ofEpochMilli(timestamp).atZone(ZoneId.systemDefault()).toLocalDate()
26 | }
27 | }
--------------------------------------------------------------------------------
/app/src/main/java/com/lateinit/rightweight/data/database/dao/HistoryDao.kt:
--------------------------------------------------------------------------------
1 | package com.lateinit.rightweight.data.database.dao
2 |
3 | import androidx.room.Dao
4 | import androidx.room.Insert
5 | import androidx.room.OnConflictStrategy
6 | import androidx.room.Query
7 | import androidx.room.Transaction
8 | import androidx.room.Update
9 | import com.lateinit.rightweight.data.database.entity.History
10 | import com.lateinit.rightweight.data.database.entity.HistoryExercise
11 | import com.lateinit.rightweight.data.database.entity.HistorySet
12 | import com.lateinit.rightweight.data.database.intermediate.HistoryWithHistoryExercises
13 | import kotlinx.coroutines.flow.Flow
14 | import java.time.LocalDate
15 |
16 | @Dao
17 | interface HistoryDao {
18 |
19 | @Insert(onConflict = OnConflictStrategy.REPLACE)
20 | suspend fun insertHistory(
21 | history: History,
22 | exercises: List,
23 | sets: List
24 | )
25 |
26 | @Insert
27 | suspend fun restoreHistory(
28 | history: List,
29 | exercises: List,
30 | sets: List
31 | )
32 |
33 | @Insert(onConflict = OnConflictStrategy.REPLACE)
34 | suspend fun insertHistorySet(set: HistorySet)
35 |
36 | @Insert(onConflict = OnConflictStrategy.REPLACE)
37 | suspend fun insertHistoryExercise(historyExercise: HistoryExercise)
38 |
39 | @Query("SELECT * FROM history WHERE date = :localDate")
40 | fun getHistoryByDate(localDate: LocalDate): Flow
41 |
42 | @Query("SELECT * FROM history ORDER BY date DESC LIMIT 1")
43 | fun getLatestHistory(): History
44 |
45 | @Transaction
46 | @Query("SELECT * FROM history WHERE date > :startDate")
47 | suspend fun getHistoryAfterDate(
48 | startDate: LocalDate,
49 | ): List
50 |
51 | @Transaction
52 | @Query("SELECT * FROM history WHERE date = :localDate")
53 | fun getHistoryWithHistoryExercisesByDate(localDate: LocalDate): Flow
54 |
55 | @Transaction
56 | @Query("SELECT * FROM history WHERE date BETWEEN :startDate AND :endDate")
57 | fun getHistoryBetweenDate(
58 | startDate: LocalDate,
59 | endDate: LocalDate
60 | ): Flow>
61 |
62 | @Query("SELECT COALESCE(MAX(`order`), 0) FROM history_exercise WHERE history_id = :historyId")
63 | suspend fun getMaxHistoryExerciseOrder(historyId: String): Int
64 |
65 | @Query("SELECT COALESCE(MAX(`order`), 0) FROM history_set WHERE exercise_id = :exerciseId")
66 | suspend fun getMaxHistorySetOrder(exerciseId: String): Int
67 |
68 | @Update
69 | suspend fun updateHistory(history: History)
70 |
71 | @Update
72 | suspend fun updateHistorySet(set: HistorySet)
73 |
74 | @Update
75 | suspend fun updateHistoryExercise(historyExercise: HistoryExercise)
76 |
77 | @Query("DELETE FROM history_set WHERE set_id = :historySetId")
78 | suspend fun removeHistorySet(historySetId: String)
79 |
80 | @Query("DELETE FROM history_exercise WHERE exercise_id = :historyExerciseId")
81 | suspend fun removeHistoryExercise(historyExerciseId: String)
82 |
83 | @Query("DELETE FROM history")
84 | suspend fun removeAllHistories()
85 |
86 | @Query("DELETE FROM history_set WHERE checked = 0")
87 | suspend fun removeUncheckedHistorySet()
88 |
89 | @Query("DELETE FROM history_exercise WHERE (SELECT count(*) FROM history_set WHERE history_set.exercise_id = history_exercise.exercise_id) = 0")
90 | suspend fun removeUncheckedHistoryExercise()
91 | }
--------------------------------------------------------------------------------
/app/src/main/java/com/lateinit/rightweight/data/database/dao/RoutineDao.kt:
--------------------------------------------------------------------------------
1 | package com.lateinit.rightweight.data.database.dao
2 |
3 | import androidx.room.Dao
4 | import androidx.room.Insert
5 | import androidx.room.OnConflictStrategy
6 | import androidx.room.Query
7 | import androidx.room.Transaction
8 | import androidx.room.Update
9 | import com.lateinit.rightweight.data.database.entity.Day
10 | import com.lateinit.rightweight.data.database.entity.Exercise
11 | import com.lateinit.rightweight.data.database.entity.ExerciseSet
12 | import com.lateinit.rightweight.data.database.entity.Routine
13 | import com.lateinit.rightweight.data.database.intermediate.DayWithExercises
14 | import com.lateinit.rightweight.data.database.intermediate.RoutineWithDays
15 | import kotlinx.coroutines.flow.Flow
16 |
17 | @Dao
18 | interface RoutineDao {
19 |
20 | @Insert(onConflict = OnConflictStrategy.REPLACE)
21 | suspend fun insertRoutine(
22 | routine: Routine,
23 | days: List,
24 | exercises: List,
25 | sets: List
26 | )
27 |
28 | @Insert
29 | suspend fun restoreRoutine(
30 | routine: List,
31 | days: List,
32 | exercises: List,
33 | sets: List
34 | )
35 |
36 | @Update
37 | suspend fun updateRoutines(routines: List)
38 |
39 | @Query("SELECT (`order`) FROM routine ORDER BY `order` DESC LIMIT 1")
40 | suspend fun getHigherRoutineOrder(): Int?
41 |
42 | @Query("SELECT * FROM routine WHERE routine_id = :routineId")
43 | suspend fun getRoutineById(routineId: String): Routine
44 |
45 | @Query("SELECT * FROM day WHERE day_id = :dayId")
46 | suspend fun getDayById(dayId: String): Day
47 |
48 | @Query("SELECT * FROM day WHERE routine_id = :routineId ORDER BY `order`")
49 | suspend fun getDaysByRoutineId(routineId: String): List
50 |
51 | @Query("SELECT * FROM exercise WHERE day_id = :dayId ORDER BY `order`")
52 | suspend fun getExercisesByDayId(dayId: String): List
53 |
54 | @Query("SELECT * FROM exercise_set WHERE exercise_id = :exerciseId ORDER BY `order`")
55 | suspend fun getSetsByExerciseId(exerciseId: String): List
56 |
57 | @Transaction
58 | @Query("SELECT * FROM routine")
59 | suspend fun getAllRoutineWithDays(): List
60 |
61 | @Query("SELECT * FROM routine ORDER BY `order`")
62 | fun getAllRoutines(): Flow>
63 |
64 | @Transaction
65 | @Query("SELECT * FROM routine WHERE routine_id = :routineId")
66 | suspend fun getRoutineWithDaysByRoutineId(routineId: String): RoutineWithDays
67 |
68 | @Transaction
69 | @Query("SELECT * FROM day WHERE day_id = :dayId")
70 | fun getDayWithExercisesByDayId(dayId: String): Flow
71 |
72 | @Query("DELETE FROM routine WHERE routine_id = :routineId")
73 | suspend fun removeRoutineById(routineId: String)
74 |
75 | @Query("DELETE FROM routine")
76 | suspend fun removeAllRoutines()
77 |
78 | }
--------------------------------------------------------------------------------
/app/src/main/java/com/lateinit/rightweight/data/database/dao/SharedRoutineDao.kt:
--------------------------------------------------------------------------------
1 | package com.lateinit.rightweight.data.database.dao
2 |
3 | import androidx.paging.PagingSource
4 | import androidx.room.*
5 | import com.lateinit.rightweight.data.database.entity.SharedRoutine
6 | import com.lateinit.rightweight.data.database.entity.SharedRoutineDay
7 | import com.lateinit.rightweight.data.database.entity.SharedRoutineExercise
8 | import com.lateinit.rightweight.data.database.entity.SharedRoutineExerciseSet
9 | import com.lateinit.rightweight.data.database.intermediate.SharedRoutineDayWithExercises
10 | import com.lateinit.rightweight.data.database.intermediate.SharedRoutineWithDays
11 | import kotlinx.coroutines.flow.Flow
12 |
13 | @Dao
14 | interface SharedRoutineDao {
15 | @Insert(onConflict = OnConflictStrategy.REPLACE)
16 | suspend fun insertSharedRoutine(
17 | sharedRoutine: SharedRoutine,
18 | )
19 |
20 | @Insert(onConflict = OnConflictStrategy.REPLACE)
21 | suspend fun insertSharedRoutineDetail(
22 | days: List,
23 | exercises: List,
24 | sets: List
25 | )
26 |
27 | @Query("DELETE FROM shared_routine")
28 | fun removeAllSharedRoutines()
29 |
30 | @Query("SELECT * FROM shared_routine")
31 | fun getAllSharedRoutinesByPaging(): PagingSource
32 |
33 | @Query("SELECT * FROM shared_routine")
34 | fun getAllSharedRoutines(): List
35 |
36 | @Transaction
37 | @Query("SELECT * FROM shared_routine WHERE routine_id = :routineId")
38 | fun getSharedRoutineWithDaysByRoutineId(routineId: String): Flow
39 | }
--------------------------------------------------------------------------------
/app/src/main/java/com/lateinit/rightweight/data/database/entity/Day.kt:
--------------------------------------------------------------------------------
1 | package com.lateinit.rightweight.data.database.entity
2 |
3 | import androidx.room.ColumnInfo
4 | import androidx.room.Entity
5 | import androidx.room.ForeignKey
6 | import androidx.room.ForeignKey.CASCADE
7 | import androidx.room.PrimaryKey
8 |
9 | @Entity(
10 | tableName = "day",
11 | foreignKeys = [
12 | ForeignKey(
13 | entity = Routine::class,
14 | parentColumns = ["routine_id"],
15 | childColumns = ["routine_id"],
16 | onDelete = CASCADE
17 | )
18 | ]
19 | )
20 | data class Day(
21 | @PrimaryKey
22 | @ColumnInfo(name = "day_id")
23 | val dayId: String,
24 | @ColumnInfo(name = "routine_id")
25 | val routineId: String,
26 | @ColumnInfo(name = "order")
27 | val order: Int
28 | )
--------------------------------------------------------------------------------
/app/src/main/java/com/lateinit/rightweight/data/database/entity/Exercise.kt:
--------------------------------------------------------------------------------
1 | package com.lateinit.rightweight.data.database.entity
2 |
3 | import androidx.room.ColumnInfo
4 | import androidx.room.Entity
5 | import androidx.room.ForeignKey
6 | import androidx.room.ForeignKey.CASCADE
7 | import androidx.room.PrimaryKey
8 | import com.lateinit.rightweight.data.model.local.ExercisePartType
9 |
10 | @Entity(
11 | tableName = "exercise",
12 | foreignKeys = [
13 | ForeignKey(
14 | entity = Day::class,
15 | parentColumns = ["day_id"],
16 | childColumns = ["day_id"],
17 | onDelete = CASCADE
18 | )
19 | ]
20 | )
21 | data class Exercise(
22 | @PrimaryKey
23 | @ColumnInfo(name = "exercise_id")
24 | val exerciseId: String,
25 | @ColumnInfo(name = "day_id")
26 | val dayId: String,
27 | @ColumnInfo(name = "title")
28 | val title: String,
29 | @ColumnInfo(name = "order")
30 | val order: Int,
31 | @ColumnInfo(name = "part")
32 | val part: ExercisePartType
33 | )
34 |
--------------------------------------------------------------------------------
/app/src/main/java/com/lateinit/rightweight/data/database/entity/ExerciseSet.kt:
--------------------------------------------------------------------------------
1 | package com.lateinit.rightweight.data.database.entity
2 |
3 | import androidx.room.ColumnInfo
4 | import androidx.room.Entity
5 | import androidx.room.ForeignKey
6 | import androidx.room.ForeignKey.CASCADE
7 | import androidx.room.PrimaryKey
8 |
9 | @Entity(
10 | tableName = "exercise_set",
11 | foreignKeys = [
12 | ForeignKey(
13 | entity = Exercise::class,
14 | parentColumns = ["exercise_id"],
15 | childColumns = ["exercise_id"],
16 | onDelete = CASCADE
17 | )
18 | ]
19 | )
20 | data class ExerciseSet(
21 | @PrimaryKey
22 | @ColumnInfo(name = "set_id")
23 | val setId: String,
24 | @ColumnInfo(name = "exercise_id")
25 | val exerciseId: String,
26 | @ColumnInfo(name = "weight")
27 | val weight: String,
28 | @ColumnInfo(name = "count")
29 | val count: String,
30 | @ColumnInfo(name = "order")
31 | val order: Int
32 | )
--------------------------------------------------------------------------------
/app/src/main/java/com/lateinit/rightweight/data/database/entity/History.kt:
--------------------------------------------------------------------------------
1 | package com.lateinit.rightweight.data.database.entity
2 |
3 | import androidx.room.ColumnInfo
4 | import androidx.room.Entity
5 | import androidx.room.PrimaryKey
6 | import java.time.LocalDate
7 |
8 | @Entity(tableName = "history")
9 | data class History(
10 | @PrimaryKey
11 | @ColumnInfo(name = "history_id")
12 | val historyId: String,
13 | @ColumnInfo(name = "date")
14 | val date: LocalDate,
15 | @ColumnInfo(name = "time")
16 | val time: String,
17 | @ColumnInfo(name = "routine_title")
18 | val routineTitle: String,
19 | @ColumnInfo(name = "day_order")
20 | val dayOrder: Int,
21 | @ColumnInfo(name = "completed")
22 | val completed: Boolean
23 | )
--------------------------------------------------------------------------------
/app/src/main/java/com/lateinit/rightweight/data/database/entity/HistoryExercise.kt:
--------------------------------------------------------------------------------
1 | package com.lateinit.rightweight.data.database.entity
2 |
3 | import androidx.room.ColumnInfo
4 | import androidx.room.Entity
5 | import androidx.room.ForeignKey
6 | import androidx.room.PrimaryKey
7 | import com.lateinit.rightweight.data.model.local.ExercisePartType
8 |
9 | @Entity(
10 | tableName = "history_exercise",
11 | foreignKeys = [
12 | ForeignKey(
13 | entity = History::class,
14 | parentColumns = ["history_id"],
15 | childColumns = ["history_id"],
16 | onDelete = ForeignKey.CASCADE
17 | )
18 | ]
19 | )
20 | data class HistoryExercise(
21 | @PrimaryKey
22 | @ColumnInfo(name = "exercise_id")
23 | val exerciseId: String,
24 | @ColumnInfo(name = "history_id")
25 | val historyId: String,
26 | @ColumnInfo(name = "title")
27 | val title: String,
28 | @ColumnInfo(name = "order")
29 | val order: Int,
30 | @ColumnInfo(name = "part")
31 | val part: ExercisePartType
32 | )
--------------------------------------------------------------------------------
/app/src/main/java/com/lateinit/rightweight/data/database/entity/HistorySet.kt:
--------------------------------------------------------------------------------
1 | package com.lateinit.rightweight.data.database.entity
2 |
3 | import androidx.room.ColumnInfo
4 | import androidx.room.Entity
5 | import androidx.room.ForeignKey
6 | import androidx.room.PrimaryKey
7 |
8 | @Entity(
9 | tableName = "history_set",
10 | foreignKeys = [
11 | ForeignKey(
12 | entity = HistoryExercise::class,
13 | parentColumns = ["exercise_id"],
14 | childColumns = ["exercise_id"],
15 | onDelete = ForeignKey.CASCADE
16 | )
17 | ]
18 | )
19 | data class HistorySet(
20 | @PrimaryKey
21 | @ColumnInfo(name = "set_id")
22 | val setId: String,
23 | @ColumnInfo(name = "exercise_id")
24 | val exerciseId: String,
25 | @ColumnInfo(name = "weight")
26 | val weight: String,
27 | @ColumnInfo(name = "count")
28 | val count: String,
29 | @ColumnInfo(name = "order")
30 | val order: Int,
31 | @ColumnInfo(name = "checked")
32 | val checked: Boolean
33 | )
34 |
--------------------------------------------------------------------------------
/app/src/main/java/com/lateinit/rightweight/data/database/entity/Routine.kt:
--------------------------------------------------------------------------------
1 | package com.lateinit.rightweight.data.database.entity
2 |
3 | import androidx.room.ColumnInfo
4 | import androidx.room.Entity
5 | import androidx.room.PrimaryKey
6 | import java.time.LocalDateTime
7 |
8 | @Entity(tableName = "routine")
9 | data class Routine(
10 | @PrimaryKey
11 | @ColumnInfo(name = "routine_id")
12 | val routineId: String,
13 | @ColumnInfo(name = "title")
14 | val title: String,
15 | @ColumnInfo(name = "author")
16 | val author: String,
17 | @ColumnInfo(name = "description")
18 | val description: String,
19 | @ColumnInfo(name = "modified_date")
20 | val modifiedDate: LocalDateTime,
21 | @ColumnInfo(name = "order")
22 | val order: Int
23 | )
24 |
--------------------------------------------------------------------------------
/app/src/main/java/com/lateinit/rightweight/data/database/entity/SharedRoutine.kt:
--------------------------------------------------------------------------------
1 | package com.lateinit.rightweight.data.database.entity
2 |
3 | import androidx.room.ColumnInfo
4 | import androidx.room.Entity
5 | import androidx.room.PrimaryKey
6 | import java.time.LocalDateTime
7 |
8 | @Entity(tableName = "shared_routine")
9 | data class SharedRoutine(
10 | @PrimaryKey
11 | @ColumnInfo(name = "routine_id")
12 | val routineId: String,
13 | @ColumnInfo(name = "title")
14 | val title: String,
15 | @ColumnInfo(name = "author")
16 | val author: String,
17 | @ColumnInfo(name = "description")
18 | val description: String,
19 | @ColumnInfo(name = "modified_date")
20 | val modifiedDate: LocalDateTime,
21 | @ColumnInfo(name = "shared_count")
22 | val sharedCount: String
23 | )
--------------------------------------------------------------------------------
/app/src/main/java/com/lateinit/rightweight/data/database/entity/SharedRoutineDay.kt:
--------------------------------------------------------------------------------
1 | package com.lateinit.rightweight.data.database.entity
2 |
3 | import androidx.room.ColumnInfo
4 | import androidx.room.Entity
5 | import androidx.room.ForeignKey
6 | import androidx.room.PrimaryKey
7 |
8 | @Entity(
9 | tableName = "shared_routine_day",
10 | foreignKeys = [
11 | ForeignKey(
12 | entity = SharedRoutine::class,
13 | parentColumns = ["routine_id"],
14 | childColumns = ["routine_id"],
15 | onDelete = ForeignKey.CASCADE
16 | )
17 | ]
18 | )
19 | data class SharedRoutineDay(
20 | @PrimaryKey
21 | @ColumnInfo(name = "day_id")
22 | val dayId: String,
23 | @ColumnInfo(name = "routine_id")
24 | val routineId: String,
25 | @ColumnInfo(name = "order")
26 | val order: Int
27 | )
--------------------------------------------------------------------------------
/app/src/main/java/com/lateinit/rightweight/data/database/entity/SharedRoutineExercise.kt:
--------------------------------------------------------------------------------
1 | package com.lateinit.rightweight.data.database.entity
2 |
3 | import androidx.room.ColumnInfo
4 | import androidx.room.Entity
5 | import androidx.room.ForeignKey
6 | import androidx.room.PrimaryKey
7 | import com.lateinit.rightweight.data.model.local.ExercisePartType
8 |
9 | @Entity(
10 | tableName = "shared_routine_exercise",
11 | foreignKeys = [
12 | ForeignKey(
13 | entity = SharedRoutineDay::class,
14 | parentColumns = ["day_id"],
15 | childColumns = ["day_id"],
16 | onDelete = ForeignKey.CASCADE
17 | )
18 | ]
19 | )
20 | data class SharedRoutineExercise(
21 | @PrimaryKey
22 | @ColumnInfo(name = "exercise_id")
23 | val exerciseId: String,
24 | @ColumnInfo(name = "day_id")
25 | val dayId: String,
26 | @ColumnInfo(name = "title")
27 | val title: String,
28 | @ColumnInfo(name = "order")
29 | val order: Int,
30 | @ColumnInfo(name = "part")
31 | val part: ExercisePartType
32 | )
--------------------------------------------------------------------------------
/app/src/main/java/com/lateinit/rightweight/data/database/entity/SharedRoutineExerciseSet.kt:
--------------------------------------------------------------------------------
1 | package com.lateinit.rightweight.data.database.entity
2 |
3 | import androidx.room.ColumnInfo
4 | import androidx.room.Entity
5 | import androidx.room.ForeignKey
6 | import androidx.room.PrimaryKey
7 |
8 | @Entity(
9 | tableName = "shared_routine_exercise_set",
10 | foreignKeys = [
11 | ForeignKey(
12 | entity = SharedRoutineExercise::class,
13 | parentColumns = ["exercise_id"],
14 | childColumns = ["exercise_id"],
15 | onDelete = ForeignKey.CASCADE
16 | )
17 | ]
18 | )
19 | data class SharedRoutineExerciseSet(
20 | @PrimaryKey
21 | @ColumnInfo(name = "set_id")
22 | val setId: String,
23 | @ColumnInfo(name = "exercise_id")
24 | val exerciseId: String,
25 | @ColumnInfo(name = "weight")
26 | val weight: String,
27 | @ColumnInfo(name = "count")
28 | val count: String,
29 | @ColumnInfo(name = "order")
30 | val order: Int
31 | )
--------------------------------------------------------------------------------
/app/src/main/java/com/lateinit/rightweight/data/database/intermediate/DayWithExercises.kt:
--------------------------------------------------------------------------------
1 | package com.lateinit.rightweight.data.database.intermediate
2 |
3 | import androidx.room.Embedded
4 | import androidx.room.Relation
5 | import com.lateinit.rightweight.data.database.entity.Day
6 | import com.lateinit.rightweight.data.database.entity.Exercise
7 |
8 | data class DayWithExercises(
9 | @Embedded val day: Day,
10 |
11 | @Relation(
12 | entity = Exercise::class,
13 | parentColumn = "day_id",
14 | entityColumn = "day_id"
15 | )
16 | val exercises: List
17 | )
--------------------------------------------------------------------------------
/app/src/main/java/com/lateinit/rightweight/data/database/intermediate/ExerciseWithSets.kt:
--------------------------------------------------------------------------------
1 | package com.lateinit.rightweight.data.database.intermediate
2 |
3 | import androidx.room.Embedded
4 | import androidx.room.Relation
5 | import com.lateinit.rightweight.data.database.entity.Exercise
6 | import com.lateinit.rightweight.data.database.entity.ExerciseSet
7 |
8 | data class ExerciseWithSets(
9 | @Embedded val exercise: Exercise,
10 |
11 | @Relation(
12 | entity = ExerciseSet::class,
13 | parentColumn = "exercise_id",
14 | entityColumn = "exercise_id"
15 | )
16 | val sets: List
17 | )
18 |
19 |
--------------------------------------------------------------------------------
/app/src/main/java/com/lateinit/rightweight/data/database/intermediate/HistoryExerciseWithHistorySets.kt:
--------------------------------------------------------------------------------
1 | package com.lateinit.rightweight.data.database.intermediate
2 |
3 | import androidx.room.Embedded
4 | import androidx.room.Relation
5 | import com.lateinit.rightweight.data.database.entity.HistoryExercise
6 | import com.lateinit.rightweight.data.database.entity.HistorySet
7 |
8 | data class HistoryExerciseWithHistorySets(
9 | @Embedded val historyExercise: HistoryExercise,
10 |
11 | @Relation(
12 | entity = HistorySet::class,
13 | parentColumn = "exercise_id",
14 | entityColumn = "exercise_id"
15 | )
16 | val historySets: List
17 | )
18 |
--------------------------------------------------------------------------------
/app/src/main/java/com/lateinit/rightweight/data/database/intermediate/HistoryWithHistoryExercises.kt:
--------------------------------------------------------------------------------
1 | package com.lateinit.rightweight.data.database.intermediate
2 |
3 | import androidx.room.Embedded
4 | import androidx.room.Relation
5 | import com.lateinit.rightweight.data.database.entity.History
6 | import com.lateinit.rightweight.data.database.entity.HistoryExercise
7 |
8 | data class HistoryWithHistoryExercises(
9 | @Embedded val history: History,
10 |
11 | @Relation(
12 | entity = HistoryExercise::class,
13 | parentColumn = "history_id",
14 | entityColumn = "history_id"
15 | )
16 | val historyExercises: List
17 | )
18 |
--------------------------------------------------------------------------------
/app/src/main/java/com/lateinit/rightweight/data/database/intermediate/RoutineWithDays.kt:
--------------------------------------------------------------------------------
1 | package com.lateinit.rightweight.data.database.intermediate
2 |
3 | import androidx.room.Embedded
4 | import androidx.room.Relation
5 | import com.lateinit.rightweight.data.database.entity.Day
6 | import com.lateinit.rightweight.data.database.entity.Routine
7 |
8 | data class RoutineWithDays(
9 | @Embedded val routine: Routine,
10 |
11 | @Relation(
12 | entity = Day::class,
13 | parentColumn = "routine_id",
14 | entityColumn = "routine_id"
15 | )
16 | val days: List
17 | )
18 |
--------------------------------------------------------------------------------
/app/src/main/java/com/lateinit/rightweight/data/database/intermediate/SharedRoutineDayWithExercises.kt:
--------------------------------------------------------------------------------
1 | package com.lateinit.rightweight.data.database.intermediate
2 |
3 | import androidx.room.Embedded
4 | import androidx.room.Relation
5 | import com.lateinit.rightweight.data.database.entity.*
6 |
7 | data class SharedRoutineDayWithExercises(
8 | @Embedded val day: SharedRoutineDay,
9 |
10 | @Relation(
11 | entity = SharedRoutineExercise::class,
12 | parentColumn = "day_id",
13 | entityColumn = "day_id"
14 | )
15 | val exercises: List
16 | )
--------------------------------------------------------------------------------
/app/src/main/java/com/lateinit/rightweight/data/database/intermediate/SharedRoutineExerciseWithExerciseSets.kt:
--------------------------------------------------------------------------------
1 | package com.lateinit.rightweight.data.database.intermediate
2 |
3 | import androidx.room.Embedded
4 | import androidx.room.Relation
5 | import com.lateinit.rightweight.data.database.entity.SharedRoutineDay
6 | import com.lateinit.rightweight.data.database.entity.SharedRoutineExercise
7 | import com.lateinit.rightweight.data.database.entity.SharedRoutineExerciseSet
8 |
9 | data class SharedRoutineExerciseWithExerciseSets(
10 | @Embedded val exercise: SharedRoutineExercise,
11 |
12 | @Relation(
13 | entity = SharedRoutineExerciseSet::class,
14 | parentColumn = "exercise_id",
15 | entityColumn = "exercise_id"
16 | )
17 | val sets: List
18 | )
--------------------------------------------------------------------------------
/app/src/main/java/com/lateinit/rightweight/data/database/intermediate/SharedRoutineWithDays.kt:
--------------------------------------------------------------------------------
1 | package com.lateinit.rightweight.data.database.intermediate
2 |
3 | import androidx.room.Embedded
4 | import androidx.room.Relation
5 | import com.lateinit.rightweight.data.database.entity.SharedRoutine
6 | import com.lateinit.rightweight.data.database.entity.SharedRoutineDay
7 |
8 | data class SharedRoutineWithDays(
9 | @Embedded val routine: SharedRoutine,
10 |
11 | @Relation(
12 | entity = SharedRoutineDay::class,
13 | parentColumn = "routine_id",
14 | entityColumn = "routine_id"
15 | )
16 | val days: List
17 | )
18 |
--------------------------------------------------------------------------------
/app/src/main/java/com/lateinit/rightweight/data/datasource/local/HistoryLocalDataSource.kt:
--------------------------------------------------------------------------------
1 | package com.lateinit.rightweight.data.datasource.local
2 |
3 | import com.lateinit.rightweight.data.database.entity.Day
4 | import com.lateinit.rightweight.data.database.entity.Exercise
5 | import com.lateinit.rightweight.data.database.entity.ExerciseSet
6 | import com.lateinit.rightweight.data.database.entity.History
7 | import com.lateinit.rightweight.data.database.entity.HistoryExercise
8 | import com.lateinit.rightweight.data.database.entity.HistorySet
9 | import com.lateinit.rightweight.data.database.intermediate.HistoryWithHistoryExercises
10 | import kotlinx.coroutines.flow.Flow
11 | import java.time.LocalDate
12 |
13 | interface HistoryLocalDataSource {
14 |
15 | suspend fun insertHistory(
16 | routineId: String,
17 | day: Day,
18 | routineTitle: String,
19 | exercises: List,
20 | exerciseSets: List
21 | )
22 |
23 | suspend fun restoreHistory(
24 | histories: List,
25 | exercises: List,
26 | sets: List
27 | )
28 |
29 | suspend fun insertHistorySet(historyExerciseId: String)
30 |
31 | suspend fun insertHistoryExercise(historyId: String)
32 |
33 | suspend fun getHistoryAfterDate(startDate: LocalDate): List
34 |
35 | fun getHistoryByDate(localDate: LocalDate): Flow
36 |
37 | fun getHistoryWithHistoryExercisesByDate(localDate: LocalDate): Flow
38 |
39 | fun getHistoryBetweenDate(
40 | startDate: LocalDate,
41 | endDate: LocalDate
42 | ): Flow>
43 |
44 | suspend fun updateHistory(history: History)
45 |
46 | suspend fun updateHistorySet(historySet: HistorySet)
47 |
48 | suspend fun updateHistoryExercise(historyExercise: HistoryExercise)
49 |
50 | suspend fun removeHistorySet(historySetId: String)
51 |
52 | suspend fun removeHistoryExercise(historyExerciseId: String)
53 |
54 | suspend fun removeAllHistories()
55 |
56 | suspend fun removeUncheckedHistorySet()
57 |
58 | suspend fun removeUncheckedHistoryExercise()
59 | }
--------------------------------------------------------------------------------
/app/src/main/java/com/lateinit/rightweight/data/datasource/local/RoutineLocalDataSource.kt:
--------------------------------------------------------------------------------
1 | package com.lateinit.rightweight.data.datasource.local
2 |
3 | import com.lateinit.rightweight.data.database.entity.Day
4 | import com.lateinit.rightweight.data.database.entity.Exercise
5 | import com.lateinit.rightweight.data.database.entity.ExerciseSet
6 | import com.lateinit.rightweight.data.database.entity.Routine
7 | import com.lateinit.rightweight.data.database.intermediate.DayWithExercises
8 | import com.lateinit.rightweight.data.database.intermediate.RoutineWithDays
9 | import kotlinx.coroutines.flow.Flow
10 |
11 | interface RoutineLocalDataSource {
12 |
13 | suspend fun insertRoutine(
14 | routine: Routine,
15 | days: List,
16 | exercises: List,
17 | sets: List
18 | )
19 |
20 | suspend fun restoreRoutines(
21 | routines: List,
22 | days: List,
23 | exercises: List,
24 | sets: List
25 | )
26 |
27 | suspend fun getRoutineById(routineId: String): Routine
28 |
29 | suspend fun getHigherRoutineOrder(): Int?
30 |
31 | suspend fun getDayById(dayId: String): Day
32 |
33 | suspend fun getDaysByRoutineId(routineId: String): List
34 |
35 | suspend fun getExercisesByDayId(dayId: String): List
36 |
37 | suspend fun getSetsByExerciseId(exerciseId: String): List
38 |
39 | suspend fun getRoutineWithDaysByRoutineId(routineId: String): RoutineWithDays
40 |
41 | suspend fun getAllRoutineWithDays(): List
42 |
43 | fun getAllRoutines(): Flow>
44 |
45 | fun getDayWithExercisesByDayId(dayId: String): Flow
46 |
47 | suspend fun updateRoutines(routines: List)
48 |
49 | suspend fun removeRoutineById(routineId: String)
50 |
51 | suspend fun removeAllRoutines()
52 | }
--------------------------------------------------------------------------------
/app/src/main/java/com/lateinit/rightweight/data/datasource/local/SharedRoutineLocalDataSource.kt:
--------------------------------------------------------------------------------
1 | package com.lateinit.rightweight.data.datasource.local
2 |
3 | import com.lateinit.rightweight.data.database.entity.SharedRoutineDay
4 | import com.lateinit.rightweight.data.database.entity.SharedRoutineExercise
5 | import com.lateinit.rightweight.data.database.entity.SharedRoutineExerciseSet
6 | import com.lateinit.rightweight.data.database.intermediate.SharedRoutineWithDays
7 | import kotlinx.coroutines.flow.Flow
8 |
9 | interface SharedRoutineLocalDataSource {
10 | suspend fun insertSharedRoutineDetail(
11 | days: List,
12 | exercises: List,
13 | sets: List
14 | )
15 |
16 | fun getSharedRoutineWithDaysByRoutineId(routineId: String): Flow
17 | }
--------------------------------------------------------------------------------
/app/src/main/java/com/lateinit/rightweight/data/datasource/local/UserLocalDataSource.kt:
--------------------------------------------------------------------------------
1 | package com.lateinit.rightweight.data.datasource.local
2 |
3 | import com.lateinit.rightweight.data.model.local.User
4 | import kotlinx.coroutines.flow.Flow
5 |
6 | interface UserLocalDataSource {
7 |
8 | suspend fun saveUser(user: User)
9 |
10 | fun getUser(): Flow
11 |
12 | suspend fun removeUserInfo()
13 | }
--------------------------------------------------------------------------------
/app/src/main/java/com/lateinit/rightweight/data/datasource/local/impl/RoutineLocalDataSourceImpl.kt:
--------------------------------------------------------------------------------
1 | package com.lateinit.rightweight.data.datasource.local.impl
2 |
3 | import com.lateinit.rightweight.data.database.dao.RoutineDao
4 | import com.lateinit.rightweight.data.database.entity.Day
5 | import com.lateinit.rightweight.data.database.entity.Exercise
6 | import com.lateinit.rightweight.data.database.entity.ExerciseSet
7 | import com.lateinit.rightweight.data.database.entity.Routine
8 | import com.lateinit.rightweight.data.database.intermediate.DayWithExercises
9 | import com.lateinit.rightweight.data.database.intermediate.RoutineWithDays
10 | import com.lateinit.rightweight.data.datasource.local.RoutineLocalDataSource
11 | import kotlinx.coroutines.flow.Flow
12 | import javax.inject.Inject
13 |
14 | class RoutineLocalDataSourceImpl @Inject constructor(
15 | private val routineDao: RoutineDao
16 | ) : RoutineLocalDataSource {
17 |
18 | override suspend fun insertRoutine(
19 | routine: Routine,
20 | days: List,
21 | exercises: List,
22 | sets: List
23 | ) {
24 | routineDao.insertRoutine(routine, days, exercises, sets)
25 | }
26 |
27 | override suspend fun restoreRoutines(
28 | routines: List,
29 | days: List,
30 | exercises: List,
31 | sets: List
32 | ) {
33 | routineDao.restoreRoutine(routines, days, exercises, sets)
34 | }
35 |
36 | override suspend fun updateRoutines(routines: List) {
37 | routineDao.updateRoutines(routines)
38 | }
39 |
40 | override suspend fun getHigherRoutineOrder(): Int? {
41 | return routineDao.getHigherRoutineOrder()
42 | }
43 |
44 | override suspend fun getRoutineById(routineId: String): Routine {
45 | return routineDao.getRoutineById(routineId)
46 | }
47 |
48 | override suspend fun getDayById(dayId: String): Day {
49 | return routineDao.getDayById(dayId)
50 | }
51 |
52 | override suspend fun getDaysByRoutineId(routineId: String): List {
53 | return routineDao.getDaysByRoutineId(routineId)
54 | }
55 |
56 | override suspend fun getExercisesByDayId(dayId: String): List {
57 | return routineDao.getExercisesByDayId(dayId)
58 | }
59 |
60 | override suspend fun getSetsByExerciseId(exerciseId: String): List {
61 | return routineDao.getSetsByExerciseId(exerciseId)
62 | }
63 |
64 | override suspend fun getRoutineWithDaysByRoutineId(routineId: String): RoutineWithDays {
65 | return routineDao.getRoutineWithDaysByRoutineId(routineId)
66 | }
67 |
68 | override fun getAllRoutines(): Flow> {
69 | return routineDao.getAllRoutines()
70 | }
71 |
72 | override suspend fun getAllRoutineWithDays(): List {
73 | return routineDao.getAllRoutineWithDays()
74 | }
75 |
76 | override fun getDayWithExercisesByDayId(dayId: String): Flow {
77 | return routineDao.getDayWithExercisesByDayId(dayId)
78 | }
79 |
80 | override suspend fun removeRoutineById(routineId: String) {
81 | return routineDao.removeRoutineById(routineId)
82 | }
83 |
84 | override suspend fun removeAllRoutines() {
85 | routineDao.removeAllRoutines()
86 | }
87 | }
--------------------------------------------------------------------------------
/app/src/main/java/com/lateinit/rightweight/data/datasource/local/impl/SharedRoutineLocalDataSourceImpl.kt:
--------------------------------------------------------------------------------
1 | package com.lateinit.rightweight.data.datasource.local.impl
2 |
3 | import com.lateinit.rightweight.data.database.dao.SharedRoutineDao
4 | import com.lateinit.rightweight.data.database.entity.SharedRoutineDay
5 | import com.lateinit.rightweight.data.database.entity.SharedRoutineExercise
6 | import com.lateinit.rightweight.data.database.entity.SharedRoutineExerciseSet
7 | import com.lateinit.rightweight.data.database.intermediate.SharedRoutineWithDays
8 | import com.lateinit.rightweight.data.datasource.local.SharedRoutineLocalDataSource
9 | import kotlinx.coroutines.flow.Flow
10 | import javax.inject.Inject
11 |
12 | class SharedRoutineLocalDataSourceImpl @Inject constructor(
13 | private val sharedRoutineDao: SharedRoutineDao
14 | ): SharedRoutineLocalDataSource {
15 | override suspend fun insertSharedRoutineDetail(
16 | days: List,
17 | exercises: List,
18 | sets: List
19 | ) {
20 | sharedRoutineDao.insertSharedRoutineDetail(days, exercises, sets)
21 | }
22 |
23 | override fun getSharedRoutineWithDaysByRoutineId(routineId: String): Flow {
24 | return sharedRoutineDao.getSharedRoutineWithDaysByRoutineId(routineId)
25 | }
26 | }
--------------------------------------------------------------------------------
/app/src/main/java/com/lateinit/rightweight/data/datasource/local/impl/UserLocalDataSourceImpl.kt:
--------------------------------------------------------------------------------
1 | package com.lateinit.rightweight.data.datasource.local.impl
2 |
3 | import com.lateinit.rightweight.data.dataStore.AppPreferencesDataStore
4 | import com.lateinit.rightweight.data.datasource.local.UserLocalDataSource
5 | import com.lateinit.rightweight.data.model.local.User
6 | import kotlinx.coroutines.flow.Flow
7 | import javax.inject.Inject
8 |
9 | class UserLocalDataSourceImpl @Inject constructor(
10 | private val appPreferencesDataStore: AppPreferencesDataStore
11 | ) : UserLocalDataSource {
12 |
13 | override suspend fun saveUser(user: User) {
14 | appPreferencesDataStore.saveUser(user)
15 | }
16 |
17 | override fun getUser(): Flow {
18 | return appPreferencesDataStore.userInfo
19 | }
20 |
21 | override suspend fun removeUserInfo() {
22 | appPreferencesDataStore.deleteUserInfo()
23 | }
24 | }
--------------------------------------------------------------------------------
/app/src/main/java/com/lateinit/rightweight/data/datasource/remote/HistoryRemoteDatasource.kt:
--------------------------------------------------------------------------------
1 | package com.lateinit.rightweight.data.datasource.remote
2 |
3 | import com.lateinit.rightweight.data.model.remote.WriteModelData
4 | import com.lateinit.rightweight.data.database.entity.History
5 | import com.lateinit.rightweight.data.database.entity.HistoryExercise
6 | import com.lateinit.rightweight.data.database.entity.HistorySet
7 | import java.time.LocalDate
8 |
9 | interface HistoryRemoteDatasource {
10 | suspend fun getLatestHistoryDate(userId: String): LocalDate
11 |
12 | suspend fun commitTransaction(writes: List)
13 |
14 | suspend fun getHistories(path: String): List
15 |
16 | suspend fun getHistoryExercises(path: String): List
17 |
18 | suspend fun getHistoryExerciseSets(path: String): List
19 | }
--------------------------------------------------------------------------------
/app/src/main/java/com/lateinit/rightweight/data/datasource/remote/LoginDataSource.kt:
--------------------------------------------------------------------------------
1 | package com.lateinit.rightweight.data.datasource.remote
2 |
3 | import com.lateinit.rightweight.data.model.remote.LoginResponse
4 |
5 | interface LoginDataSource {
6 |
7 | suspend fun login(key: String, token: String): LoginResponse
8 |
9 | suspend fun deleteAccount(key: String, idToken: String)
10 | }
--------------------------------------------------------------------------------
/app/src/main/java/com/lateinit/rightweight/data/datasource/remote/RoutineRemoteDataSource.kt:
--------------------------------------------------------------------------------
1 | package com.lateinit.rightweight.data.datasource.remote
2 |
3 | import com.lateinit.rightweight.data.database.entity.Day
4 | import com.lateinit.rightweight.data.database.entity.Exercise
5 | import com.lateinit.rightweight.data.database.entity.ExerciseSet
6 | import com.lateinit.rightweight.data.database.entity.Routine
7 | import com.lateinit.rightweight.data.model.remote.DocumentResponse
8 | import com.lateinit.rightweight.data.remote.model.RoutineField
9 |
10 | interface RoutineRemoteDataSource {
11 | suspend fun getRoutineByUserId(userId: String): List>
12 |
13 | suspend fun getRoutine(routineId: String): Routine
14 |
15 | suspend fun getRoutineDays(routineId: String): List
16 |
17 | suspend fun getRoutineExercises(path: String): List
18 |
19 | suspend fun getRoutineExerciseSets(path: String): List
20 |
21 | suspend fun getChildrenDocumentName(path: String): List
22 | }
--------------------------------------------------------------------------------
/app/src/main/java/com/lateinit/rightweight/data/datasource/remote/SharedRoutineRemoteDataSource.kt:
--------------------------------------------------------------------------------
1 | package com.lateinit.rightweight.data.datasource.remote
2 |
3 | import androidx.paging.PagingData
4 | import com.lateinit.rightweight.data.database.entity.SharedRoutine
5 | import com.lateinit.rightweight.data.database.entity.SharedRoutineDay
6 | import com.lateinit.rightweight.data.database.entity.SharedRoutineExercise
7 | import com.lateinit.rightweight.data.database.entity.SharedRoutineExerciseSet
8 | import com.lateinit.rightweight.data.model.remote.SharedRoutineSortType
9 | import com.lateinit.rightweight.data.model.remote.WriteModelData
10 | import com.lateinit.rightweight.data.remote.model.SharedRoutineField
11 | import kotlinx.coroutines.flow.Flow
12 |
13 | interface SharedRoutineRemoteDataSource {
14 |
15 | suspend fun getSharedRoutine(routineId: String): SharedRoutineField?
16 |
17 | suspend fun getSharedRoutineDays(routineId: String): List
18 |
19 | suspend fun getSharedRoutineExercises(
20 | routineId: String,
21 | dayId: String
22 | ): List
23 |
24 | suspend fun getSharedRoutineExerciseSets(
25 | routineId: String,
26 | dayId: String,
27 | exerciseId: String
28 | ): List
29 |
30 | fun getSharedRoutinesByPaging(): Flow>
31 |
32 | suspend fun setSharedRoutineSortType(sortType: SharedRoutineSortType)
33 |
34 | suspend fun getChildrenDocumentName(path: String): List
35 |
36 | suspend fun commitTransaction(writes: List)
37 | }
--------------------------------------------------------------------------------
/app/src/main/java/com/lateinit/rightweight/data/datasource/remote/UserRemoteDataSource.kt:
--------------------------------------------------------------------------------
1 | package com.lateinit.rightweight.data.datasource.remote
2 |
3 | import com.lateinit.rightweight.data.remote.model.UserInfoField
4 |
5 | interface UserRemoteDataSource {
6 | suspend fun backupUserInfo(userId: String, routineId: String, dayId: String, completedDayId: String)
7 |
8 | suspend fun getChildrenDocumentName(path: String): List
9 |
10 | suspend fun restoreUserInfo(userId: String): UserInfoField?
11 | }
--------------------------------------------------------------------------------
/app/src/main/java/com/lateinit/rightweight/data/datasource/remote/impl/HistoryRemoteDataSourceImpl.kt:
--------------------------------------------------------------------------------
1 | package com.lateinit.rightweight.data.datasource.remote.impl
2 |
3 | import com.lateinit.rightweight.data.api.UserApiService
4 | import com.lateinit.rightweight.data.database.entity.History
5 | import com.lateinit.rightweight.data.database.entity.HistoryExercise
6 | import com.lateinit.rightweight.data.database.entity.HistorySet
7 | import com.lateinit.rightweight.data.datasource.remote.HistoryRemoteDatasource
8 | import com.lateinit.rightweight.data.mapper.toHistory
9 | import com.lateinit.rightweight.data.mapper.toHistoryExercise
10 | import com.lateinit.rightweight.data.mapper.toHistorySet
11 | import com.lateinit.rightweight.data.model.remote.Direction
12 | import com.lateinit.rightweight.data.model.remote.FiledReferenceData
13 | import com.lateinit.rightweight.data.model.remote.FromData
14 | import com.lateinit.rightweight.data.model.remote.OrderByData
15 | import com.lateinit.rightweight.data.model.remote.RunQueryBody
16 | import com.lateinit.rightweight.data.model.remote.StructuredQueryData
17 | import com.lateinit.rightweight.data.model.remote.WriteModelData
18 | import com.lateinit.rightweight.data.model.remote.WriteRequestBody
19 | import java.time.LocalDate
20 | import java.time.format.DateTimeFormatter
21 | import javax.inject.Inject
22 |
23 | class HistoryRemoteDataSourceImpl @Inject constructor(
24 | private val api: UserApiService
25 | ) : HistoryRemoteDatasource {
26 | override suspend fun getLatestHistoryDate(userId: String): LocalDate {
27 | val documentResponseList = api.getLastHistoryDate(
28 | userId,
29 | RunQueryBody(
30 | StructuredQueryData(
31 | from = FromData("history"),
32 | orderBy = listOf(
33 | OrderByData(
34 | FiledReferenceData("date"),
35 | Direction.DESCENDING.toString()
36 | )
37 | ),
38 | limit = 1
39 | )
40 | )
41 | )
42 | val formatter = DateTimeFormatter.ofPattern("yyyy-MM-dd'T'HH:mm:ss'Z'")
43 | val lastDateTime = documentResponseList.first()
44 | .document?.fields?.date?.value ?: return DEFAULT_LOCAL_DATE
45 | return LocalDate.parse(lastDateTime, formatter)
46 | }
47 |
48 | override suspend fun commitTransaction(writes: List) {
49 | api.commitTransaction(WriteRequestBody(writes))
50 | }
51 |
52 | override suspend fun getHistories(path: String): List{
53 | val histories = api.getHistories(path)
54 | return histories.documents?.map {
55 | val historyId = it.name.split("/").last()
56 | it.fields.toHistory(historyId)
57 | } ?: emptyList()
58 | }
59 |
60 | override suspend fun getHistoryExercises(path: String): List {
61 | val exercises = api.getHistoryExercises(path)
62 | return exercises.documents?.map {
63 | val exerciseId = it.name.split("/").last()
64 | it.fields.toHistoryExercise(exerciseId)
65 | } ?: emptyList()
66 | }
67 |
68 | override suspend fun getHistoryExerciseSets(path: String): List {
69 | val exerciseSets = api.getHistoryExerciseSets(path)
70 | return exerciseSets.documents?.map {
71 | val exerciseSetId = it.name.split("/").last()
72 | it.fields.toHistorySet(exerciseSetId)
73 | } ?: emptyList()
74 | }
75 |
76 | companion object {
77 | val DEFAULT_LOCAL_DATE: LocalDate = LocalDate.parse("1990-01-01")
78 | }
79 | }
--------------------------------------------------------------------------------
/app/src/main/java/com/lateinit/rightweight/data/datasource/remote/impl/LoginDataSourceImpl.kt:
--------------------------------------------------------------------------------
1 | package com.lateinit.rightweight.data.datasource.remote.impl
2 |
3 | import com.lateinit.rightweight.data.api.AuthApiService
4 | import com.lateinit.rightweight.data.model.remote.LoginResponse
5 | import com.lateinit.rightweight.data.datasource.remote.LoginDataSource
6 | import com.lateinit.rightweight.data.model.remote.LoginRequestBody
7 | import com.lateinit.rightweight.data.model.remote.PostBody
8 | import javax.inject.Inject
9 |
10 | class LoginDataSourceImpl @Inject constructor(
11 | val api: AuthApiService
12 | ) : LoginDataSource {
13 |
14 | override suspend fun login(key: String, token: String): LoginResponse {
15 | val postBody = PostBody(token, "google.com").toString()
16 | return api.loginToFirebase(
17 | key, LoginRequestBody(
18 | postBody, "http://localhost",
19 | returnIdpCredential = true,
20 | returnSecureToken = true
21 | )
22 | )
23 | }
24 |
25 | override suspend fun deleteAccount(key: String, idToken: String) {
26 | api.deleteAccount(key, idToken)
27 | }
28 | }
--------------------------------------------------------------------------------
/app/src/main/java/com/lateinit/rightweight/data/datasource/remote/impl/RoutineRemoteDataSourceImpl.kt:
--------------------------------------------------------------------------------
1 | package com.lateinit.rightweight.data.datasource.remote.impl
2 |
3 | import com.lateinit.rightweight.data.api.RoutineApiService
4 | import com.lateinit.rightweight.data.database.entity.Day
5 | import com.lateinit.rightweight.data.database.entity.Exercise
6 | import com.lateinit.rightweight.data.database.entity.ExerciseSet
7 | import com.lateinit.rightweight.data.database.entity.Routine
8 | import com.lateinit.rightweight.data.datasource.remote.RoutineRemoteDataSource
9 | import com.lateinit.rightweight.data.mapper.local.toDay
10 | import com.lateinit.rightweight.data.mapper.local.toExercise
11 | import com.lateinit.rightweight.data.mapper.local.toExerciseSet
12 | import com.lateinit.rightweight.data.mapper.local.toRoutine
13 | import com.lateinit.rightweight.data.model.remote.DocumentResponse
14 | import com.lateinit.rightweight.data.model.remote.FiledReferenceData
15 | import com.lateinit.rightweight.data.model.remote.FilterData
16 | import com.lateinit.rightweight.data.model.remote.FilterOperator
17 | import com.lateinit.rightweight.data.model.remote.FromData
18 | import com.lateinit.rightweight.data.model.remote.RunQueryBody
19 | import com.lateinit.rightweight.data.model.remote.StructuredQueryData
20 | import com.lateinit.rightweight.data.model.remote.WhereData
21 | import com.lateinit.rightweight.data.remote.model.RoutineField
22 | import com.lateinit.rightweight.data.remote.model.StringValue
23 | import javax.inject.Inject
24 |
25 | class RoutineRemoteDataSourceImpl @Inject constructor(
26 | private val api: RoutineApiService
27 | ) : RoutineRemoteDataSource {
28 | override suspend fun getRoutineByUserId(userId: String): List> {
29 | return api.getUserRoutine(
30 | RunQueryBody(
31 | StructuredQueryData(
32 | from = FromData("routine"),
33 | where = WhereData(
34 | FilterData(
35 | FiledReferenceData("userId"),
36 | FilterOperator.EQUAL.toString(),
37 | StringValue(userId)
38 | )
39 | )
40 | )
41 | )
42 | )
43 | }
44 |
45 | override suspend fun getRoutine(routineId: String): Routine {
46 | return api.getRoutine(routineId).fields.toRoutine(routineId)
47 | }
48 |
49 | override suspend fun getRoutineDays(routineId: String): List {
50 | val path = "routine/${routineId}/day"
51 | val days = api.getDays(path)
52 | return days.documents?.map {
53 | val dayId = it.name.split("/").last()
54 | it.fields.toDay(dayId)
55 | } ?: emptyList()
56 | }
57 |
58 | override suspend fun getRoutineExercises(path: String): List {
59 | val exercises = api.getExercises(path)
60 | return exercises.documents?.map {
61 | val exerciseId = it.name.split("/").last()
62 | it.fields.toExercise(exerciseId)
63 | } ?: emptyList()
64 | }
65 |
66 | override suspend fun getRoutineExerciseSets(path: String): List {
67 | val exerciseSets = api.getExerciseSets(path)
68 | return exerciseSets.documents?.map {
69 | val exerciseSetId = it.name.split("/").last()
70 | it.fields.toExerciseSet(exerciseSetId)
71 | } ?: emptyList()
72 | }
73 |
74 | override suspend fun getChildrenDocumentName(path: String): List {
75 | val documentNameList = api.getChildrenDocument(path)
76 | return documentNameList.documents?.map {
77 | it.name.split("/").last()
78 | } ?: emptyList()
79 | }
80 | }
--------------------------------------------------------------------------------
/app/src/main/java/com/lateinit/rightweight/data/datasource/remote/impl/UserRemoteDataSourceImpl.kt:
--------------------------------------------------------------------------------
1 | package com.lateinit.rightweight.data.datasource.remote.impl
2 |
3 | import com.lateinit.rightweight.data.api.UserApiService
4 | import com.lateinit.rightweight.data.datasource.remote.UserRemoteDataSource
5 | import com.lateinit.rightweight.data.remote.model.RootField
6 | import com.lateinit.rightweight.data.remote.model.StringValue
7 | import com.lateinit.rightweight.data.remote.model.UserInfoField
8 | import javax.inject.Inject
9 |
10 | class UserRemoteDataSourceImpl @Inject constructor(
11 | private val api: UserApiService
12 | ) : UserRemoteDataSource {
13 | override suspend fun backupUserInfo(userId: String, routineId: String, dayId: String, completedDayId: String) {
14 | api.backupUserInfo(
15 | userId, RootField(
16 | UserInfoField(
17 | routineId = StringValue(routineId),
18 | dayId = StringValue(dayId),
19 | completedDayId = StringValue(completedDayId)
20 | )
21 | )
22 | )
23 | }
24 |
25 |
26 | override suspend fun restoreUserInfo(userId: String): UserInfoField? {
27 | val response = api.restoreUserInfo(userId)
28 | return if (response.isSuccessful) {
29 | response.body()?.fields
30 | } else null
31 | }
32 |
33 | override suspend fun getChildrenDocumentName(path: String): List {
34 | val documentNameList = api.getChildrenDocumentName(path)
35 | return documentNameList.documents?.map {
36 | it.name.split("/").last()
37 | } ?: emptyList()
38 | }
39 |
40 | }
--------------------------------------------------------------------------------
/app/src/main/java/com/lateinit/rightweight/data/mapper/local/ToExercisePartType.kt:
--------------------------------------------------------------------------------
1 | package com.lateinit.rightweight.data.mapper
2 |
3 | import com.lateinit.rightweight.data.model.local.ExercisePartType
4 | import com.lateinit.rightweight.ui.model.routine.ExercisePartTypeUiModel
5 |
6 | fun ExercisePartTypeUiModel.toExercisePartType(): ExercisePartType {
7 | return when (this) {
8 | ExercisePartTypeUiModel.CHEST -> ExercisePartType.CHEST
9 | ExercisePartTypeUiModel.BACK -> ExercisePartType.BACK
10 | ExercisePartTypeUiModel.LEG -> ExercisePartType.LEG
11 | ExercisePartTypeUiModel.SHOULDER -> ExercisePartType.SHOULDER
12 | ExercisePartTypeUiModel.BICEPS -> ExercisePartType.BICEPS
13 | ExercisePartTypeUiModel.TRICEPS -> ExercisePartType.TRICEPS
14 | ExercisePartTypeUiModel.CORE -> ExercisePartType.CORE
15 | ExercisePartTypeUiModel.FOREARM -> ExercisePartType.FOREARM
16 | ExercisePartTypeUiModel.CARDIO -> ExercisePartType.CARDIO
17 | }
18 | }
--------------------------------------------------------------------------------
/app/src/main/java/com/lateinit/rightweight/data/mapper/local/ToHistory.kt:
--------------------------------------------------------------------------------
1 | package com.lateinit.rightweight.data.mapper
2 |
3 | import com.lateinit.rightweight.data.database.entity.History
4 | import com.lateinit.rightweight.data.database.entity.HistoryExercise
5 | import com.lateinit.rightweight.data.database.entity.HistorySet
6 | import com.lateinit.rightweight.data.model.local.ExercisePartType
7 | import com.lateinit.rightweight.data.remote.model.HistoryExerciseField
8 | import com.lateinit.rightweight.data.remote.model.HistoryExerciseSetField
9 | import com.lateinit.rightweight.data.remote.model.HistoryField
10 | import com.lateinit.rightweight.ui.model.history.HistoryExerciseSetUiModel
11 | import com.lateinit.rightweight.ui.model.history.HistoryExerciseUiModel
12 | import com.lateinit.rightweight.ui.model.history.HistoryUiModel
13 | import com.lateinit.rightweight.util.DEFAULT_SET_COUNT
14 | import com.lateinit.rightweight.util.DEFAULT_SET_WEIGHT
15 | import java.time.LocalDate
16 | import java.time.format.DateTimeFormatter
17 |
18 | fun HistoryUiModel.toHistory(): History {
19 | return History(
20 | historyId = historyId,
21 | date = date,
22 | time = time,
23 | routineTitle = routineTitle,
24 | dayOrder = order,
25 | completed = completed
26 | )
27 | }
28 |
29 | fun HistoryExerciseUiModel.toHistoryExercise(): HistoryExercise {
30 | return HistoryExercise(
31 | exerciseId = exerciseId,
32 | historyId = historyId,
33 | title = title,
34 | order = order,
35 | part = part.toExercisePartType()
36 | )
37 | }
38 |
39 | fun HistoryExerciseSetUiModel.toHistorySet(): HistorySet {
40 | return HistorySet(
41 | setId = setId,
42 | exerciseId = exerciseId,
43 | weight = weight.ifEmpty { DEFAULT_SET_WEIGHT },
44 | count = count.ifEmpty { DEFAULT_SET_COUNT },
45 | order = order,
46 | checked = checked
47 | )
48 | }
49 |
50 | fun HistoryField.toHistory(historyId: String): History {
51 | val refinedDateString = date.value
52 | val formatter = DateTimeFormatter.ofPattern("yyyy-MM-dd'T'HH:mm:ss'Z'")
53 | val date = LocalDate.parse(refinedDateString, formatter)
54 |
55 | return History(
56 | historyId = historyId,
57 | date = date,
58 | time = time.value,
59 | routineTitle = routineTitle.value,
60 | dayOrder = order.value.toInt(),
61 | completed = true
62 | )
63 | }
64 |
65 | fun HistoryExerciseField.toHistoryExercise(exerciseId: String): HistoryExercise {
66 | return HistoryExercise(
67 | exerciseId = exerciseId,
68 | historyId = historyId.value,
69 | title = title.value,
70 | order = order.value.toInt(),
71 | part = ExercisePartType.valueOf(part.value)
72 | )
73 | }
74 |
75 | fun HistoryExerciseSetField.toHistorySet(exerciseSetId: String): HistorySet {
76 | return HistorySet(
77 | setId = exerciseSetId,
78 | exerciseId = exerciseId.value,
79 | weight = weight.value,
80 | count = count.value,
81 | order = order.value.toInt(),
82 | checked = true
83 | )
84 | }
--------------------------------------------------------------------------------
/app/src/main/java/com/lateinit/rightweight/data/mapper/local/ToSharedRoutine.kt:
--------------------------------------------------------------------------------
1 | package com.lateinit.rightweight.data.mapper
2 |
3 | import com.lateinit.rightweight.data.database.entity.SharedRoutineDay
4 | import com.lateinit.rightweight.data.database.entity.SharedRoutineExercise
5 | import com.lateinit.rightweight.data.database.entity.SharedRoutineExerciseSet
6 | import com.lateinit.rightweight.data.model.local.ExercisePartType
7 | import com.lateinit.rightweight.data.model.remote.DetailResponse
8 | import com.lateinit.rightweight.data.remote.model.DayField
9 | import com.lateinit.rightweight.data.remote.model.ExerciseField
10 | import com.lateinit.rightweight.data.remote.model.ExerciseSetField
11 |
12 | fun DetailResponse.toSharedRoutineDay(): SharedRoutineDay {
13 | val splitedName = name.split("/")
14 | return SharedRoutineDay(
15 | routineId = fields.routineId.value.toString(),
16 | dayId = splitedName.last(),
17 | order = fields.order.value.toString().toInt()
18 | )
19 | }
20 |
21 | fun DetailResponse.toSharedRoutineExercise(): SharedRoutineExercise {
22 | val splitedName = name.split("/")
23 | return SharedRoutineExercise(
24 | dayId = fields.dayId.value.toString(),
25 | exerciseId = splitedName.last(),
26 | title = fields.title.value.toString(),
27 | order = fields.order.value.toString().toInt(),
28 | part = ExercisePartType.valueOf(fields.partType.value.toString())
29 | )
30 | }
31 |
32 | fun DetailResponse.toSharedRoutineExerciseSet(): SharedRoutineExerciseSet {
33 | val splitedName = name.split("/")
34 | return SharedRoutineExerciseSet(
35 | exerciseId = fields.exerciseId.value.toString(),
36 | setId = splitedName.last(),
37 | weight = fields.weight.value.toString(),
38 | count = fields.count.value.toString(),
39 | order = fields.order.value.toString().toInt()
40 | )
41 | }
--------------------------------------------------------------------------------
/app/src/main/java/com/lateinit/rightweight/data/mapper/local/ToSharedRoutineSortType.kt:
--------------------------------------------------------------------------------
1 | package com.lateinit.rightweight.data.mapper.local
2 |
3 | import com.lateinit.rightweight.data.model.remote.SharedRoutineSortType
4 | import com.lateinit.rightweight.ui.model.shared.SharedRoutineSortTypeUiModel
5 |
6 | fun SharedRoutineSortTypeUiModel.toSharedRoutineSortType(): SharedRoutineSortType {
7 | return when (this) {
8 | SharedRoutineSortTypeUiModel.MODIFIED_DATE_FIRST -> SharedRoutineSortType.MODIFIED_DATE_FIRST
9 | SharedRoutineSortTypeUiModel.SHARED_COUNT_FIRST -> SharedRoutineSortType.SHARED_COUNT_FIRST
10 | }
11 | }
--------------------------------------------------------------------------------
/app/src/main/java/com/lateinit/rightweight/data/mapper/remote/ToHisttoryField.kt:
--------------------------------------------------------------------------------
1 | package com.lateinit.rightweight.data.mapper.remote
2 |
3 | import com.lateinit.rightweight.data.remote.model.HistoryExerciseField
4 | import com.lateinit.rightweight.data.remote.model.HistoryExerciseSetField
5 | import com.lateinit.rightweight.data.remote.model.HistoryField
6 | import com.lateinit.rightweight.data.remote.model.IntValue
7 | import com.lateinit.rightweight.data.remote.model.StringValue
8 | import com.lateinit.rightweight.data.remote.model.TimeStampValue
9 | import com.lateinit.rightweight.ui.model.history.HistoryExerciseSetUiModel
10 | import com.lateinit.rightweight.ui.model.history.HistoryExerciseUiModel
11 | import com.lateinit.rightweight.ui.model.history.HistoryUiModel
12 |
13 | fun HistoryUiModel.toHistoryField(): HistoryField {
14 | return HistoryField(
15 | date = TimeStampValue(date.toString() + "T00:00:00Z"),
16 | time = StringValue(time),
17 | routineTitle = StringValue(routineTitle),
18 | order = IntValue(order.toString())
19 | )
20 | }
21 |
22 | fun HistoryExerciseUiModel.toHistoryExerciseField(): HistoryExerciseField {
23 | return HistoryExerciseField(
24 | historyId = StringValue(historyId),
25 | title = StringValue(title),
26 | order = IntValue(order.toString()),
27 | part = StringValue(part.name),
28 | )
29 | }
30 |
31 | fun HistoryExerciseSetUiModel.toHistoryExerciseSetField(): HistoryExerciseSetField {
32 | return HistoryExerciseSetField(
33 | exerciseId = StringValue(exerciseId),
34 | weight = StringValue(weight),
35 | count = StringValue(count),
36 | order = IntValue(order.toString()),
37 | )
38 | }
--------------------------------------------------------------------------------
/app/src/main/java/com/lateinit/rightweight/data/mapper/remote/ToRoutineField.kt:
--------------------------------------------------------------------------------
1 | package com.lateinit.rightweight.data.mapper.remote
2 |
3 | import com.lateinit.rightweight.data.remote.model.DayField
4 | import com.lateinit.rightweight.data.remote.model.ExerciseField
5 | import com.lateinit.rightweight.data.remote.model.ExerciseSetField
6 | import com.lateinit.rightweight.data.remote.model.IntValue
7 | import com.lateinit.rightweight.data.remote.model.RoutineField
8 | import com.lateinit.rightweight.data.remote.model.StringValue
9 | import com.lateinit.rightweight.data.remote.model.TimeStampValue
10 | import com.lateinit.rightweight.ui.model.routine.DayUiModel
11 | import com.lateinit.rightweight.ui.model.routine.ExerciseSetUiModel
12 | import com.lateinit.rightweight.ui.model.routine.ExerciseUiModel
13 | import com.lateinit.rightweight.ui.model.routine.RoutineUiModel
14 |
15 | fun RoutineUiModel.toRoutineField(userId: String): RoutineField {
16 | return RoutineField(
17 | author = StringValue(author),
18 | description = StringValue(description),
19 | modifiedDate = TimeStampValue(modifiedDate.toString() + "Z"),
20 | order = IntValue(order.toString()),
21 | title = StringValue(title),
22 | userId = StringValue(userId),
23 | )
24 | }
25 |
26 | fun DayUiModel.toDayField(): DayField {
27 | return DayField(
28 | order = IntValue(order.toString()),
29 | routineId = StringValue(routineId)
30 | )
31 | }
32 |
33 | fun ExerciseUiModel.toExerciseField(): ExerciseField {
34 | return ExerciseField(
35 | order = IntValue(order.toString()),
36 | partType = StringValue(part.name),
37 | title = StringValue(title),
38 | dayId = StringValue(dayId)
39 | )
40 | }
41 |
42 | fun ExerciseSetUiModel.toExerciseSetField(): ExerciseSetField {
43 | return ExerciseSetField(
44 | order = IntValue(order.toString()),
45 | count = StringValue(count),
46 | weight = StringValue(weight),
47 | exerciseId = StringValue(exerciseId)
48 | )
49 | }
--------------------------------------------------------------------------------
/app/src/main/java/com/lateinit/rightweight/data/mapper/remote/ToSharedRoutineField.kt:
--------------------------------------------------------------------------------
1 | package com.lateinit.rightweight.data.mapper.remote
2 |
3 | import com.lateinit.rightweight.data.remote.model.IntValue
4 | import com.lateinit.rightweight.data.remote.model.MapValue
5 | import com.lateinit.rightweight.data.remote.model.MapValueRootField
6 | import com.lateinit.rightweight.data.remote.model.SharedCount
7 | import com.lateinit.rightweight.data.remote.model.SharedRoutineField
8 | import com.lateinit.rightweight.data.remote.model.StringValue
9 | import com.lateinit.rightweight.data.remote.model.TimeStampValue
10 | import com.lateinit.rightweight.ui.model.routine.RoutineUiModel
11 | import java.time.LocalDateTime
12 |
13 | fun RoutineUiModel.toSharedRoutineField(userId: String): SharedRoutineField {
14 | return SharedRoutineField(
15 | author = StringValue(author),
16 | description = StringValue(description),
17 | modifiedDate = TimeStampValue(modifiedDate.toString() + "Z"),
18 | order = IntValue(order.toString()),
19 | title = StringValue(title),
20 | userId = StringValue(userId),
21 | sharedCount = MapValue(
22 | MapValueRootField(
23 | SharedCount(
24 | time = TimeStampValue(LocalDateTime.now().toString() + "Z"),
25 | count = IntValue("0")
26 | )
27 | )
28 | )
29 | )
30 | }
--------------------------------------------------------------------------------
/app/src/main/java/com/lateinit/rightweight/data/model/local/ExercisePartType.kt:
--------------------------------------------------------------------------------
1 | package com.lateinit.rightweight.data.model.local
2 |
3 | enum class ExercisePartType {
4 | CHEST,
5 | BACK,
6 | LEG,
7 | SHOULDER,
8 | BICEPS,
9 | TRICEPS,
10 | CORE,
11 | FOREARM,
12 | CARDIO
13 | }
--------------------------------------------------------------------------------
/app/src/main/java/com/lateinit/rightweight/data/model/local/User.kt:
--------------------------------------------------------------------------------
1 | package com.lateinit.rightweight.data.model.local
2 |
3 | data class User(
4 | val userId: String,
5 | val routineId: String,
6 | val dayId: String,
7 | val completedDayId: String = "",
8 | val email: String,
9 | val displayName: String,
10 | val photoUrl: String,
11 | val idToken: String
12 | )
13 |
--------------------------------------------------------------------------------
/app/src/main/java/com/lateinit/rightweight/data/model/remote/DataValue.kt:
--------------------------------------------------------------------------------
1 | package com.lateinit.rightweight.data.remote.model
2 |
3 | import com.google.gson.annotations.SerializedName
4 |
5 | sealed class ValueData
6 |
7 | data class StringValue(
8 | @SerializedName("stringValue")
9 | val value: String
10 | ): ValueData()
11 |
12 | data class IntValue(
13 | @SerializedName("integerValue")
14 | val value: String
15 | ): ValueData()
16 |
17 | data class TimeStampValue(
18 | @SerializedName("timestampValue")
19 | val value: String
20 | ): ValueData()
21 |
22 | data class MapValue(
23 | @SerializedName("mapValue")
24 | val value: MapValueRootField
25 | ): ValueData()
--------------------------------------------------------------------------------
/app/src/main/java/com/lateinit/rightweight/data/model/remote/Documents.kt:
--------------------------------------------------------------------------------
1 | package com.lateinit.rightweight.data.model.remote
2 |
3 | data class DocumentResponse(val document: DetailResponse?)
4 |
5 | data class DocumentsResponse(val documents: List>?)
6 |
7 | data class DetailResponse (val name: String, val fields: T)
--------------------------------------------------------------------------------
/app/src/main/java/com/lateinit/rightweight/data/model/remote/LoginModel.kt:
--------------------------------------------------------------------------------
1 | package com.lateinit.rightweight.data.model.remote
2 |
3 |
4 | data class LoginRequestBody(
5 | val postBody: String,
6 | val requestUri: String,
7 | val returnIdpCredential: Boolean,
8 | val returnSecureToken: Boolean
9 | )
10 |
11 | data class PostBody(
12 | val id_token: String,
13 | val providerId: String,
14 | ) {
15 | override fun toString(): String {
16 | return "id_token=$id_token&providerId=$providerId"
17 | }
18 | }
--------------------------------------------------------------------------------
/app/src/main/java/com/lateinit/rightweight/data/model/remote/LoginResponse.kt:
--------------------------------------------------------------------------------
1 | package com.lateinit.rightweight.data.model.remote
2 |
3 | data class LoginResponse(
4 | val federatedId: String,
5 | val providerId: String,
6 | val localId: String,
7 | val emailVerified: String,
8 | val email: String,
9 | val oauthIdToken: String,
10 | val firstName: String,
11 | val lastName: String,
12 | val fullName: String,
13 | val displayName: String,
14 | val idToken: String,
15 | val photoUrl: String,
16 | val refreshToken: String,
17 | val expiresIn: String,
18 | val rawUserInfo: String
19 | )
--------------------------------------------------------------------------------
/app/src/main/java/com/lateinit/rightweight/data/model/remote/RootField.kt:
--------------------------------------------------------------------------------
1 | package com.lateinit.rightweight.data.remote.model
2 |
3 | import com.google.gson.annotations.SerializedName
4 |
5 | data class RootField(
6 | @SerializedName("fields")
7 | val remoteData: RemoteData
8 | )
9 |
10 | data class MapValueRootField(
11 | @SerializedName("fields")
12 | val remoteData: SharedCount
13 | )
--------------------------------------------------------------------------------
/app/src/main/java/com/lateinit/rightweight/data/model/remote/RunQueryModel.kt:
--------------------------------------------------------------------------------
1 | package com.lateinit.rightweight.data.model.remote
2 |
3 | import com.lateinit.rightweight.data.remote.model.ValueData
4 |
5 | data class RunQueryBody(
6 | val structuredQuery: StructuredQueryData
7 | )
8 |
9 | data class StructuredQueryData(
10 | val from: FromData,
11 | val where: WhereData? = null,
12 | val orderBy: List? = null,
13 | val limit: Int? = null,
14 | val startAt: StartAtData? = null
15 | )
16 |
17 | data class FromData(
18 | val collectionId: String,
19 | )
20 |
21 | data class WhereData(
22 | val fieldFilter: FilterData
23 | )
24 |
25 | data class FilterData(
26 | val field: FiledReferenceData,
27 | val op: String,
28 | val value: ValueData
29 | )
30 |
31 | data class FiledReferenceData(
32 | val fieldPath: String
33 | )
34 |
35 | data class OrderByData(
36 | val field: FiledReferenceData,
37 | val direction: String
38 | )
39 |
40 | data class StartAtData(
41 | val values: List
42 | )
43 |
44 | enum class SharedRoutineSortType{
45 | MODIFIED_DATE_FIRST,
46 | SHARED_COUNT_FIRST
47 | }
48 |
49 | enum class FilterOperator {
50 | //https://firebase.google.com/docs/firestore/reference/rest/v1/StructuredQuery#operator_1
51 | EQUAL,
52 | NOT_EQUAL,
53 | }
54 |
55 | enum class Direction{
56 | ASCENDING,
57 | DESCENDING
58 | }
--------------------------------------------------------------------------------
/app/src/main/java/com/lateinit/rightweight/data/model/remote/WriteModel.kt:
--------------------------------------------------------------------------------
1 | package com.lateinit.rightweight.data.model.remote
2 |
3 | import com.lateinit.rightweight.data.remote.model.IntValue
4 | import com.lateinit.rightweight.data.remote.model.RemoteData
5 |
6 | data class WriteRequestBody(
7 | val writes: List
8 | )
9 |
10 | data class WriteModelData(
11 | val transform: TransformData? = null,
12 | val update: UpdateData? = null,
13 | val delete: String? = null,
14 | ){
15 | companion object{
16 | const val defaultPath = "projects/right-weight/databases/(default)/documents"
17 | }
18 | }
19 |
20 | data class UpdateData(
21 | val name: String,
22 | val fields: RemoteData
23 | )
24 |
25 | data class TransformData(
26 | val document: String,
27 | val fieldTransforms: List
28 | )
29 |
30 | data class FieldTransformsModelData(
31 | val fieldPath: String,
32 | val increment: IntValue
33 | )
--------------------------------------------------------------------------------
/app/src/main/java/com/lateinit/rightweight/data/repository/HistoryRepository.kt:
--------------------------------------------------------------------------------
1 | package com.lateinit.rightweight.data.repository
2 |
3 | import com.lateinit.rightweight.data.database.entity.Day
4 | import com.lateinit.rightweight.data.database.entity.Exercise
5 | import com.lateinit.rightweight.data.database.entity.ExerciseSet
6 | import com.lateinit.rightweight.data.database.entity.History
7 | import com.lateinit.rightweight.data.database.intermediate.HistoryWithHistoryExercises
8 | import com.lateinit.rightweight.data.model.remote.WriteModelData
9 | import com.lateinit.rightweight.ui.model.history.HistoryExerciseSetUiModel
10 | import com.lateinit.rightweight.ui.model.history.HistoryExerciseUiModel
11 | import com.lateinit.rightweight.ui.model.history.HistoryUiModel
12 | import kotlinx.coroutines.flow.Flow
13 | import java.time.LocalDate
14 |
15 | interface HistoryRepository {
16 |
17 | suspend fun saveHistory(
18 | routineId: String,
19 | day: Day,
20 | routineTitle: String,
21 | exercises: List,
22 | exerciseSets: List
23 | )
24 |
25 | suspend fun insertHistorySet(historyExerciseId: String)
26 |
27 | suspend fun insertHistoryExercise(historyId: String)
28 |
29 | suspend fun getLatestHistoryDate(userId: String): LocalDate
30 |
31 | suspend fun getHistoryAfterDate(startDate: LocalDate): List
32 |
33 | suspend fun restoreHistory(userId: String)
34 |
35 | fun getHistoryByDate(localDate: LocalDate): Flow
36 |
37 | fun getHistoryWithHistoryExercisesByDate(localDate: LocalDate): Flow
38 |
39 | fun getHistoryBetweenDate(
40 | startDate: LocalDate,
41 | endDate: LocalDate
42 | ): Flow