1
0

Compare commits

...

115 Commits

Author SHA1 Message Date
763543a16e Merge branch 'release/0.17.4' 2020-04-23 19:24:54 +02:00
acabe90c9f Version 0.17.4 2020-04-23 19:24:49 +02:00
f79da9003a Merge tag '0.17.3' into develop
Version 0.17.3
2020-04-23 16:22:49 +02:00
fc9e558cd6 Merge branch 'release/0.17.3' 2020-04-23 16:22:44 +02:00
68140bd544 Version 0.17.3 2020-04-23 16:22:39 +02:00
2c4c2d1f49 Fix injector of ErrorDialog (#780) 2020-04-23 11:07:18 +02:00
4894086d9d Bump about_libraries from 8.1.1 to 8.1.2 (#779) 2020-04-21 16:21:44 +00:00
1d29ef5fe3 Merge tag '0.17.2' into develop
Version 0.17.2
2020-04-19 23:42:00 +02:00
7fa333cff2 Merge branch 'release/0.17.2' 2020-04-19 23:41:53 +02:00
c1ffc2ae72 Version 0.17.2 2020-04-19 23:37:29 +02:00
9c0e2dc533 Refresh semesters if previous list was downloaded in different m… (#776) 2020-04-19 23:21:59 +02:00
9b18e3669d Fix crash after send message when activity is in background (#777) 2020-04-19 23:21:25 +02:00
366ebc781d Add error message and bug report button to error dialog (#778) 2020-04-19 23:20:55 +02:00
4bd0459155 Don't log common errors to crashlytics (#775) 2020-04-18 23:07:20 +02:00
b19084cb57 Fix visibility of dialog close button when homework content is l… (#774) 2020-04-18 23:06:05 +02:00
69be7ca412 Bump kotlin_version from 1.3.71 to 1.3.72 (#773) 2020-04-17 21:01:41 +00:00
07307b9709 Bump swiperefreshlayout from 1.1.0-beta01 to 1.1.0-rc01 (#770) 2020-04-17 20:59:02 +00:00
ee4a5e56a9 Bump gradle from 3.6.2 to 3.6.3 (#772) 2020-04-17 20:37:38 +00:00
c8f8ec77a9 Bump preference-ktx from 1.1.0 to 1.1.1 (#771) 2020-04-17 20:35:24 +00:00
be46a43427 Merge tag '0.17.1' into develop
Version 0.17.1
2020-04-12 19:20:59 +02:00
183e379223 Merge branch 'release/0.17.1' 2020-04-12 19:20:53 +02:00
2350fc2ddf Version 0.17.1 2020-04-12 19:20:44 +02:00
152f966a66 Bump firebase-inappmessaging-display-ktx from 19.0.4 to 19.0.5 (#767) 2020-04-12 17:19:06 +00:00
85ee7fad1d Bump firebase-inappmessaging-ktx from 19.0.4 to 19.0.5 (#768) 2020-04-12 16:58:23 +00:00
3ac085573f Show all known adfslight registers in register list (#766) 2020-04-12 18:55:16 +02:00
64a19d9627 Bump about_libraries from 8.1.0 to 8.1.1 (#769) 2020-04-12 15:14:08 +00:00
76af623c94 Add Sdk.init(student) call in all remote repositories (#764) 2020-04-12 15:13:35 +02:00
11c285be01 Fix homework dialog size (#765) 2020-04-12 15:12:25 +02:00
a0528496eb Fix crash caused by updating view in not attached fragment (#763) 2020-04-09 23:46:42 +02:00
299345b864 Fix crash in message preview (#762) 2020-04-09 23:30:56 +02:00
0a18fefb1f Use recycler view in homework details dialog (#761) 2020-04-08 18:17:20 +02:00
a26f0ec8c8 Merge tag '0.17.0' into develop
Version 0.17.0
2020-04-05 18:42:42 +02:00
232d8d38bd Merge branch 'release/0.17.0' 2020-04-05 18:42:36 +02:00
4833e1e130 Version 0.17.0 2020-04-05 18:35:00 +02:00
bb30cf2ce3 Revert "Add "System theme" option to widgets" (#753) 2020-04-05 18:32:57 +02:00
c9b35bed7e Bump chucker from 3.1.1 to 3.2.0 (#755) 2020-04-05 16:22:50 +00:00
999672fcc3 Bump threetenbp from 1.4.2 to 1.4.3 (#756) 2020-04-05 15:32:18 +00:00
6a0ce3a58d Add force sync feature in settings (#643) 2020-04-05 16:46:49 +02:00
3612326628 Add missing sdk initialization in lucky number repository (#752) 2020-04-04 20:59:44 +02:00
bf61dd1bad Add more details in email template (#751) 2020-04-04 20:57:50 +02:00
18c1153e12 Add mark as done feature in homework (#743) 2020-04-03 17:39:36 +02:00
651be69ad2 Add firebase messaging (#740) 2020-04-02 22:47:10 +02:00
394e3bb79c Add firebase messaging (#740) 2020-04-02 22:43:03 +02:00
502a98b70a Add message attachments (#734) 2020-04-02 20:27:53 +02:00
da357775ff Add better validation to login/email field (#741) 2020-04-02 20:27:14 +02:00
c0adeaadfd Add "System theme" option to widgets (#739) 2020-04-02 20:26:28 +02:00
358c87528a Update gradle to 6.2.2 (#750) 2020-04-02 00:34:24 +02:00
0cb4866f40 Bump appcompat from 1.2.0-alpha03 to 1.2.0-beta01 (#749) 2020-04-01 22:21:25 +00:00
6ec13c896d Bump about_libraries from 8.0.2 to 8.1.0 (#747) 2020-04-01 22:01:41 +00:00
a0587a8bce Bump fragment-ktx from 1.2.3 to 1.2.4 (#748) 2020-04-01 22:00:50 +00:00
184c9413f8 Bump firebase-core from 17.2.3 to 17.3.0 (#746) 2020-04-01 18:58:26 +00:00
6440820dc5 Bump gradle from 3.6.1 to 3.6.2 (#744) 2020-04-01 18:56:41 +00:00
d9322b0df4 Bump aboutlibraries-core from 7.1.0 to 8.0.0 (#731) 2020-03-29 18:55:00 +02:00
b9a19b60e4 Bump appcompat from 1.1.0 to 1.2.0-alpha03 to fix webview crash… (#737) 2020-03-29 14:38:39 +02:00
6f697eff47 Add points to notes (#738) 2020-03-29 14:26:56 +02:00
d9c8bb399b Change strings.xml form from male to impersonal (#736) 2020-03-28 19:51:22 +01:00
2137b6c225 Bump threetenabp from 1.2.2 to 1.2.3 (#735) 2020-03-28 10:56:07 +00:00
0320079d02 Bump chucker from 2.0.4 to 3.1.1 (#733) 2020-03-28 11:44:09 +01:00
95a833ea85 Bump room from 2.2.4 to 2.2.5 (#727) 2020-03-24 22:04:25 +00:00
a85a4fe7a0 Bump kotlin_version from 1.3.70 to 1.3.71 (#732) 2020-03-24 20:30:48 +00:00
f94b8c9be8 Bump threetenbp from 1.4.1 to 1.4.2 (#730) 2020-03-24 19:53:59 +00:00
5dfe9cdd4f Bump work_manager from 2.3.3 to 2.3.4 (#728) 2020-03-24 19:52:47 +00:00
9a83b43d57 Bump fragment-ktx from 1.2.2 to 1.2.3 (#729) 2020-03-24 19:52:33 +00:00
7d21babd38 Bump rxjava from 2.2.18 to 2.2.19 (#726) 2020-03-14 22:25:05 +00:00
f763a42323 Bump mockito-inline from 3.3.1 to 3.3.3 (#725) 2020-03-14 22:20:14 +00:00
478596c4e6 Fix marking message as read in hybrid and mobile api mode (#722) 2020-03-14 23:19:59 +01:00
37842a3603 Bump dagger from 2.26 to 2.27 (#724) 2020-03-14 22:19:47 +00:00
1775e2fe62 Bump mockito-android from 3.3.1 to 3.3.3 (#723) 2020-03-14 22:18:34 +00:00
68b26d5e2b Update gradle-publisher to 2.7.2 (#719) 2020-03-07 13:38:15 +01:00
6304395050 Bump swiperefreshlayout from 1.1.0-alpha03 to 1.1.0-beta01 (#718) 2020-03-05 10:59:07 +00:00
fa3c357665 Bump work_manager from 2.3.2 to 2.3.3 (#717) 2020-03-05 10:58:38 +00:00
83282aeab6 Merge tag '0.16.0' into develop
Version 0.16.0
2020-03-05 09:47:43 +01:00
5de2e9afbd Merge branch 'release/0.16.0' 2020-03-05 09:47:37 +01:00
cd99c6b2aa Version 0.16.0 2020-03-05 09:20:46 +01:00
42aacb755c Add some login help messages (#716) 2020-03-04 22:39:28 +01:00
a880b3a9db Bump kotlin_version from 1.3.61 to 1.3.70 (#715)
Bumps `kotlin_version` from 1.3.61 to 1.3.70.

Updates `kotlin-gradle-plugin` from 1.3.61 to 1.3.70

Updates `kotlin-stdlib-jdk8` from 1.3.61 to 1.3.70
- [Release notes](https://github.com/JetBrains/kotlin/releases)
- [Changelog](https://github.com/JetBrains/kotlin/blob/master/ChangeLog.md)
- [Commits](https://github.com/JetBrains/kotlin/compare/v1.3.61...v1.3.70)

Updates `kotlin-test` from 1.3.61 to 1.3.70
- [Release notes](https://github.com/JetBrains/kotlin/releases)
- [Changelog](https://github.com/JetBrains/kotlin/blob/master/ChangeLog.md)
- [Commits](https://github.com/JetBrains/kotlin/compare/v1.3.61...v1.3.70)

Signed-off-by: dependabot-preview[bot] <support@dependabot.com>
2020-03-04 16:39:13 +01:00
7837fae2aa Add German language (#712) 2020-03-03 22:20:57 +01:00
70e9f025bb Replace Creators with Contributors (#675) 2020-03-03 18:07:38 +01:00
ab1d9b358e Change asset name and contributor name (#714) 2020-03-03 18:06:37 +01:00
2634c270b1 Set missing styles to small lesson items (#707) 2020-03-02 22:45:56 +01:00
79bd2fccdf Replace Maybe with Single in Message DAO (#710) 2020-03-02 22:31:55 +01:00
87107ec474 Filter lucky numbers by school shortcut (#708) 2020-03-02 22:22:41 +01:00
8aaa066142 Update Ukrainian language (#711) 2020-03-02 21:31:02 +01:00
5b7d465064 Add Ukrainian language (#709) 2020-03-02 20:56:53 +01:00
75c94865e4 Sort the second group's lessons below the student's lessons (#706) 2020-02-29 23:07:47 +01:00
f294e3d57c Add separate host in login form to login to VULCAN adfslight (#704) 2020-02-29 10:30:20 +01:00
565114a2d2 Update gradle to 6.2.1 (#705) 2020-02-29 02:37:58 +01:00
be057dd63c Show list of charts in grade statistics (#689) 2020-02-29 02:19:48 +01:00
e61c2bced8 Add new notifications categories (#685) 2020-02-29 01:15:26 +01:00
3abfb9f819 Bump gradle from 3.6.0 to 3.6.1 (#702) 2020-02-28 23:19:38 +00:00
7c86fabd7b Bump firebase-core from 17.2.2 to 17.2.3 (#703) 2020-02-28 23:19:00 +00:00
59f2d4b0f3 Bump gradle from 3.5.3 to 3.6.0 (#698) 2020-02-27 21:22:37 +00:00
8571586b0c Bump room from 2.2.3 to 2.2.4 (#694) 2020-02-27 21:11:48 +00:00
e21de811e2 Bump mockito-android from 3.2.4 to 3.3.1 (#696) 2020-02-27 20:35:50 +00:00
7b502ce9a8 Bump mockito-inline from 3.2.4 to 3.3.1 (#693) 2020-02-27 20:35:28 +00:00
33447d2ada Bump fragment-ktx from 1.2.0 to 1.2.2 (#695) 2020-02-27 20:35:05 +00:00
7f6b2ec096 Bump coil from 0.9.4 to 0.9.5 (#699) 2020-02-27 20:33:25 +00:00
2c35117dfa Bump rxjava from 2.2.17 to 2.2.18 (#700) 2020-02-27 20:32:38 +00:00
5b2ca07506 Bump work_manager from 2.3.0 to 2.3.2 (#697) 2020-02-27 20:30:36 +00:00
18d6ec6961 Add account recover (#635) 2020-02-27 00:10:11 +01:00
96c1bb4c69 Automatically switch semesters without sync (#681) 2020-02-24 00:24:40 +01:00
00f5b9431e Add log viewer (#686) 2020-02-22 21:24:06 +01:00
9a87df7315 Respect user settings in timetable app widget (#687) 2020-02-22 20:42:02 +01:00
30e43501ac Refactor the resizing of the lucky number app widget (#682) 2020-02-14 10:04:53 +01:00
34738a4839 Show semester in appbar subtitle in grades view (#684) 2020-02-14 09:58:58 +01:00
1cc2080cb9 Bump material from 1.1.0-rc02 to 1.1.0 (#680) 2020-02-05 00:22:51 +00:00
0826e45a25 Bump coil from 0.9.2 to 0.9.4 (#679) 2020-02-05 00:22:12 +00:00
6925204019 Fix showing empty total summary and ordering of summary months (#678) 2020-02-05 00:53:07 +01:00
bdbf1fe304 Add dynamic nick/email in login (#676) 2020-02-05 00:42:49 +01:00
720a530a6c Disable signed in students in login (#677) 2020-02-04 09:43:24 +01:00
2f56f7e4a4 Bump dagger from 2.25.4 to 2.26 (#673) 2020-02-02 15:50:12 +00:00
c3a6842027 Add total attendance summary (#672) 2020-02-02 16:40:00 +01:00
731afbb00c Fix login more options button in dark theme (#674) 2020-02-02 16:38:14 +01:00
fb3853dc70 Fix timetable_show_whole_class_entries en translation (#668) 2020-01-30 00:13:34 +01:00
ec5503678a Merge tag '0.15.0' into develop
Version 0.15.0
2020-01-26 18:15:16 +01:00
308 changed files with 13430 additions and 1959 deletions

1
.gitignore vendored
View File

@ -63,6 +63,7 @@ captures/
.idea/dynamic.xml .idea/dynamic.xml
.idea/uiDesigner.xml .idea/uiDesigner.xml
.idea/runConfigurations.xml .idea/runConfigurations.xml
.idea/discord.xml
# Keystore files # Keystore files
*.jks *.jks

View File

@ -1,9 +1,6 @@
<component name="ProjectCodeStyleConfiguration"> <component name="ProjectCodeStyleConfiguration">
<code_scheme name="Project" version="173"> <code_scheme name="Project" version="173">
<option name="LINE_SEPARATOR" value="&#10;" /> <option name="LINE_SEPARATOR" value="&#10;" />
<AndroidXmlCodeStyleSettings>
<option name="ARRANGEMENT_SETTINGS_MIGRATED_TO_191" value="true" />
</AndroidXmlCodeStyleSettings>
<JetCodeStyleSettings> <JetCodeStyleSettings>
<option name="PACKAGES_TO_USE_STAR_IMPORTS"> <option name="PACKAGES_TO_USE_STAR_IMPORTS">
<value> <value>

View File

@ -4,7 +4,7 @@ jdk: oraclejdk8
env: env:
global: global:
- ANDROID_API_LEVEL=29 - ANDROID_API_LEVEL=29
- ANDROID_BUILD_TOOLS_VERSION=29.0.2 - ANDROID_BUILD_TOOLS_VERSION=29.0.3
cache: cache:
directories: directories:
@ -14,7 +14,7 @@ cache:
branches: branches:
only: only:
- develop - develop
- 0.15.0 - 0.17.4
android: android:
licenses: licenses:
@ -49,9 +49,9 @@ script:
- ./gradlew dependencies --stacktrace --daemon - ./gradlew dependencies --stacktrace --daemon
- fossa --no-ansi || true - fossa --no-ansi || true
#- ./gradlew lintPlayRelease -x fabricGenerateResourcesPlayRelease --stacktrace --daemon #- ./gradlew lintPlayRelease -x fabricGenerateResourcesPlayRelease --stacktrace --daemon
- ./gradlew testPlayDebugUnitTest -x fabricGenerateResourcesPlay --stacktrace --daemon - ./gradlew -Pcoverage testPlayDebugUnitTest -x fabricGenerateResourcesPlay --stacktrace --daemon
- ./gradlew createFdroidDebugCoverageReport --stacktrace --daemon - ./gradlew -Pcoverage createFdroidDebugCoverageReport --stacktrace --daemon
- ./gradlew jacocoTestReport --stacktrace --daemon - ./gradlew -Pcoverage jacocoTestReport --stacktrace --daemon
- if [ -z ${SONAR_HOST+x} ]; then echo "sonar scan skipped"; else - if [ -z ${SONAR_HOST+x} ]; then echo "sonar scan skipped"; else
git fetch --unshallow; git fetch --unshallow;
./gradlew sonarqube -x test -x lint -x fabricGenerateResourcesPlayRelease -x fabricGenerateResourcesFdroidRelease -Dsonar.host.url=$SONAR_HOST -Dsonar.organization=$SONAR_ORG -Dsonar.login=$SONAR_KEY -Dsonar.branch.name=${TRAVIS_PULL_REQUEST_BRANCH:-$TRAVIS_BRANCH} --stacktrace --daemon; ./gradlew sonarqube -x test -x lint -x fabricGenerateResourcesPlayRelease -x fabricGenerateResourcesFdroidRelease -Dsonar.host.url=$SONAR_HOST -Dsonar.organization=$SONAR_ORG -Dsonar.login=$SONAR_KEY -Dsonar.branch.name=${TRAVIS_PULL_REQUEST_BRANCH:-$TRAVIS_BRANCH} --stacktrace --daemon;

View File

@ -4,21 +4,22 @@ apply plugin: 'kotlin-kapt'
apply plugin: 'kotlin-android-extensions' apply plugin: 'kotlin-android-extensions'
apply plugin: 'io.fabric' apply plugin: 'io.fabric'
apply plugin: 'com.github.triplet.play' apply plugin: 'com.github.triplet.play'
apply plugin: 'com.mikepenz.aboutlibraries.plugin'
apply from: 'jacoco.gradle' apply from: 'jacoco.gradle'
apply from: 'sonarqube.gradle' apply from: 'sonarqube.gradle'
apply from: 'hooks.gradle' apply from: 'hooks.gradle'
android { android {
compileSdkVersion 29 compileSdkVersion 29
buildToolsVersion '29.0.2' buildToolsVersion '29.0.3'
defaultConfig { defaultConfig {
applicationId "io.github.wulkanowy" applicationId "io.github.wulkanowy"
testApplicationId "io.github.tests.wulkanowy" testApplicationId "io.github.tests.wulkanowy"
minSdkVersion 16 minSdkVersion 17
targetSdkVersion 29 targetSdkVersion 29
versionCode 52 versionCode 57
versionName "0.15.0" versionName "0.17.4"
multiDexEnabled true multiDexEnabled true
testInstrumentationRunner "androidx.test.runner.AndroidJUnitRunner" testInstrumentationRunner "androidx.test.runner.AndroidJUnitRunner"
vectorDrawables.useSupportLibrary = true vectorDrawables.useSupportLibrary = true
@ -61,7 +62,7 @@ android {
buildConfigField "boolean", "CRASHLYTICS_ENABLED", project.hasProperty("enableCrashlytics") ? "true" : "false" buildConfigField "boolean", "CRASHLYTICS_ENABLED", project.hasProperty("enableCrashlytics") ? "true" : "false"
applicationIdSuffix ".dev" applicationIdSuffix ".dev"
versionNameSuffix "-dev" versionNameSuffix "-dev"
testCoverageEnabled = true testCoverageEnabled = project.hasProperty('coverage')
ext.enableCrashlytics = project.hasProperty("enableCrashlytics") ext.enableCrashlytics = project.hasProperty("enableCrashlytics")
} }
} }
@ -96,6 +97,10 @@ android {
exclude 'META-INF/library_release.kotlin_module' exclude 'META-INF/library_release.kotlin_module'
exclude 'META-INF/library-core_release.kotlin_module' exclude 'META-INF/library-core_release.kotlin_module'
} }
aboutLibraries {
configPath = "app/src/main/res/raw"
}
} }
androidExtensions { androidExtensions {
@ -110,10 +115,11 @@ play {
} }
ext { ext {
work_manager = "2.3.0" work_manager = "2.3.4"
room = "2.2.3" room = "2.2.5"
dagger = "2.25.4" dagger = "2.27"
chucker = "2.0.4" // don't update https://github.com/ChuckerTeam/chucker/issues/242
chucker = "3.2.0"
mockk = "1.9.2" mockk = "1.9.2"
} }
@ -122,24 +128,24 @@ configurations.all {
} }
dependencies { dependencies {
implementation "io.github.wulkanowy:sdk:0.15.0" implementation "io.github.wulkanowy:sdk:0.17.4"
implementation "org.jetbrains.kotlin:kotlin-stdlib-jdk8:$kotlin_version" implementation "org.jetbrains.kotlin:kotlin-stdlib-jdk8:$kotlin_version"
implementation "androidx.core:core-ktx:1.2.0-rc01" implementation "androidx.core:core-ktx:1.2.0"
implementation "androidx.activity:activity-ktx:1.1.0" implementation "androidx.activity:activity-ktx:1.1.0"
implementation "androidx.appcompat:appcompat:1.1.0" implementation "androidx.appcompat:appcompat:1.2.0-beta01"
implementation "androidx.appcompat:appcompat-resources:1.1.0" implementation "androidx.appcompat:appcompat-resources:1.1.0"
implementation "androidx.fragment:fragment-ktx:1.2.0" implementation "androidx.fragment:fragment-ktx:1.2.4"
implementation "androidx.annotation:annotation:1.1.0" implementation "androidx.annotation:annotation:1.1.0"
implementation "androidx.multidex:multidex:2.0.1" implementation "androidx.multidex:multidex:2.0.1"
implementation "androidx.preference:preference-ktx:1.1.0" implementation "androidx.preference:preference-ktx:1.1.1"
implementation "androidx.recyclerview:recyclerview:1.1.0" implementation "androidx.recyclerview:recyclerview:1.1.0"
implementation "androidx.viewpager:viewpager:1.0.0" implementation "androidx.viewpager:viewpager:1.0.0"
implementation "androidx.swiperefreshlayout:swiperefreshlayout:1.1.0-alpha03" implementation "androidx.swiperefreshlayout:swiperefreshlayout:1.1.0-rc01"
implementation "androidx.constraintlayout:constraintlayout:1.1.3" implementation "androidx.constraintlayout:constraintlayout:1.1.3"
implementation "androidx.coordinatorlayout:coordinatorlayout:1.1.0" implementation "androidx.coordinatorlayout:coordinatorlayout:1.1.0"
implementation "com.google.android.material:material:1.1.0-rc02" implementation "com.google.android.material:material:1.1.0"
implementation "com.github.wulkanowy:material-chips-input:2.0.1" implementation "com.github.wulkanowy:material-chips-input:2.0.1"
implementation "com.github.PhilJay:MPAndroidChart:v3.1.0" implementation "com.github.PhilJay:MPAndroidChart:v3.1.0"
implementation "me.zhanghai.android.materialprogressbar:library:1.6.1" implementation "me.zhanghai.android.materialprogressbar:library:1.6.1"
@ -148,6 +154,8 @@ dependencies {
implementation "androidx.work:work-rxjava2:$work_manager" implementation "androidx.work:work-rxjava2:$work_manager"
implementation "androidx.work:work-gcm:$work_manager" implementation "androidx.work:work-gcm:$work_manager"
implementation 'com.github.PaulinaSadowska:RxWorkManagerObservers:1.0.0'
implementation "androidx.room:room-runtime:$room" implementation "androidx.room:room-runtime:$room"
implementation "androidx.room:room-rxjava2:$room" implementation "androidx.room:room-rxjava2:$room"
implementation "androidx.room:room-ktx:$room" implementation "androidx.room:room-ktx:$room"
@ -163,33 +171,37 @@ dependencies {
implementation "eu.davidea:flexible-adapter-ui:1.0.0" implementation "eu.davidea:flexible-adapter-ui:1.0.0"
implementation "com.aurelhubert:ahbottomnavigation:2.3.4" implementation "com.aurelhubert:ahbottomnavigation:2.3.4"
implementation "com.ncapdevi:frag-nav:3.3.0" implementation "com.ncapdevi:frag-nav:3.3.0"
implementation "com.github.YarikSOffice:lingver:1.1.0" implementation "com.github.YarikSOffice:lingver:1.2.1"
implementation "com.github.pwittchen:reactivenetwork-rx2:3.0.6" implementation "com.github.pwittchen:reactivenetwork-rx2:3.0.6"
implementation "io.reactivex.rxjava2:rxandroid:2.1.1" implementation "io.reactivex.rxjava2:rxandroid:2.1.1"
implementation "io.reactivex.rxjava2:rxjava:2.2.17" implementation "io.reactivex.rxjava2:rxjava:2.2.19"
implementation "com.google.code.gson:gson:2.8.6" implementation "com.google.code.gson:gson:2.8.6"
implementation "com.jakewharton.threetenabp:threetenabp:1.2.2" implementation "com.jakewharton.threetenabp:threetenabp:1.2.3"
implementation "com.jakewharton.timber:timber:4.7.1" implementation "com.jakewharton.timber:timber:4.7.1"
implementation "at.favre.lib:slf4j-timber:1.0.1" implementation "at.favre.lib:slf4j-timber:1.0.1"
implementation "com.mikepenz:aboutlibraries-core:7.1.0" implementation "fr.bipi.treessence:treessence:0.3.2"
implementation "com.mikepenz:aboutlibraries-core:$about_libraries"
implementation 'com.wdullaer:materialdatetimepicker:4.2.3' implementation 'com.wdullaer:materialdatetimepicker:4.2.3'
implementation "io.coil-kt:coil:0.9.5"
implementation("io.coil-kt:coil:0.9.2") playImplementation 'com.google.firebase:firebase-analytics:17.3.0'
playImplementation 'com.google.firebase:firebase-inappmessaging-display-ktx:19.0.5'
playImplementation "com.google.firebase:firebase-core:17.2.2" playImplementation "com.google.firebase:firebase-inappmessaging-ktx:19.0.5"
playImplementation "com.google.firebase:firebase-messaging:20.1.0"
playImplementation "com.crashlytics.sdk.android:crashlytics:2.10.1" playImplementation "com.crashlytics.sdk.android:crashlytics:2.10.1"
playImplementation 'com.google.guava:listenablefuture:9999.0-empty-to-avoid-conflict-with-guava'
releaseImplementation "fr.o80.chucker:library-no-op:$chucker" releaseImplementation "com.github.ChuckerTeam.Chucker:library-no-op:$chucker"
debugImplementation "fr.o80.chucker:library:$chucker" debugImplementation "com.github.ChuckerTeam.Chucker:library:$chucker"
debugImplementation "com.amitshekhar.android:debug-db:1.0.6" debugImplementation "com.amitshekhar.android:debug-db:1.0.6"
testImplementation "junit:junit:4.13" testImplementation "junit:junit:4.13"
testImplementation "io.mockk:mockk:$mockk" testImplementation "io.mockk:mockk:$mockk"
testImplementation "org.threeten:threetenbp:1.4.1" testImplementation "org.threeten:threetenbp:1.4.3"
testImplementation "org.mockito:mockito-inline:3.2.4" testImplementation "org.mockito:mockito-inline:3.3.3"
androidTestImplementation "androidx.test:core:1.2.0" androidTestImplementation "androidx.test:core:1.2.0"
androidTestImplementation "androidx.test:runner:1.2.0" androidTestImplementation "androidx.test:runner:1.2.0"
@ -197,7 +209,7 @@ dependencies {
androidTestImplementation "io.mockk:mockk-android:$mockk" androidTestImplementation "io.mockk:mockk-android:$mockk"
androidTestImplementation "androidx.room:room-testing:$room" androidTestImplementation "androidx.room:room-testing:$room"
androidTestImplementation "org.jetbrains.kotlin:kotlin-test:$kotlin_version" androidTestImplementation "org.jetbrains.kotlin:kotlin-test:$kotlin_version"
androidTestImplementation "org.mockito:mockito-android:3.2.4" androidTestImplementation "org.mockito:mockito-android:3.3.3"
} }
apply plugin: 'com.google.gms.google-services' apply plugin: 'com.google.gms.google-services'

View File

@ -43,3 +43,10 @@
#Config for Material Components #Config for Material Components
-keep class com.google.android.material.tabs.** { *; } -keep class com.google.android.material.tabs.** { *; }
#Config for About Libraries
-keep class .R
-keep class **.R$* {
<fields>;
}

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

View File

@ -8,7 +8,6 @@ import io.github.wulkanowy.data.db.entities.Semester
import org.junit.Assert.assertEquals import org.junit.Assert.assertEquals
import org.junit.Assert.assertTrue import org.junit.Assert.assertTrue
import org.junit.Test import org.junit.Test
import org.threeten.bp.LocalDate.now
import org.threeten.bp.LocalDate.of import org.threeten.bp.LocalDate.of
import kotlin.test.assertFalse import kotlin.test.assertFalse
import kotlin.test.assertTrue import kotlin.test.assertTrue
@ -104,45 +103,45 @@ class Migration13Test : AbstractMigrationTest() {
val db = helper.runMigrationsAndValidate(dbName, 13, true, Migration13()) val db = helper.runMigrationsAndValidate(dbName, 13, true, Migration13())
val semesters1 = getSemesters(db, "SELECT * FROM Semesters WHERE student_id = 1 AND class_id = 5") val semesters1 = getSemesters(db, "SELECT * FROM Semesters WHERE student_id = 1 AND class_id = 5")
assertTrue { semesters1.single { it.isCurrent }.isCurrent } assertTrue { semesters1.single { it.second }.second }
semesters1[0].run { semesters1[0].run {
assertFalse(isCurrent) assertFalse(second)
assertEquals(1, semesterId) assertEquals(1, first.semesterId)
assertEquals(1, diaryId) assertEquals(1, first.diaryId)
} }
semesters1[2].run { semesters1[2].run {
assertFalse(isCurrent) assertFalse(second)
assertEquals(3, semesterId) assertEquals(3, first.semesterId)
assertEquals(2, diaryId) assertEquals(2, first.diaryId)
} }
semesters1[3].run { semesters1[3].run {
assertTrue(isCurrent) assertTrue(second)
assertEquals(4, semesterId) assertEquals(4, first.semesterId)
assertEquals(2, diaryId) assertEquals(2, first.diaryId)
} }
getSemesters(db, "SELECT * FROM Semesters WHERE student_id = 2 AND class_id = 5").let { getSemesters(db, "SELECT * FROM Semesters WHERE student_id = 2 AND class_id = 5").let {
assertTrue { it.single { it.isCurrent }.isCurrent } assertTrue { it.single { it.second }.second }
assertEquals(1970, it[0].schoolYear) assertEquals(1970, it[0].first.schoolYear)
assertEquals(of(1970, 1, 1), it[0].end) assertEquals(of(1970, 1, 1), it[0].first.end)
assertEquals(of(1970, 1, 1), it[0].start) assertEquals(of(1970, 1, 1), it[0].first.start)
assertFalse(it[0].isCurrent) assertFalse(it[0].second)
assertFalse(it[1].isCurrent) assertFalse(it[1].second)
assertFalse(it[2].isCurrent) assertFalse(it[2].second)
assertTrue(it[3].isCurrent) assertTrue(it[3].second)
} }
getSemesters(db, "SELECT * FROM Semesters WHERE student_id = 2 AND class_id = 5").let { getSemesters(db, "SELECT * FROM Semesters WHERE student_id = 2 AND class_id = 5").let {
assertTrue { it.single { it.isCurrent }.isCurrent } assertTrue { it.single { it.second }.second }
assertFalse(it[0].isCurrent) assertFalse(it[0].second)
assertFalse(it[1].isCurrent) assertFalse(it[1].second)
assertFalse(it[2].isCurrent) assertFalse(it[2].second)
assertTrue(it[3].isCurrent) assertTrue(it[3].second)
} }
} }
private fun getSemesters(db: SupportSQLiteDatabase, query: String): List<Semester> { private fun getSemesters(db: SupportSQLiteDatabase, query: String): List<Pair<Semester, Boolean>> {
val semesters = mutableListOf<Semester>() val semesters = mutableListOf<Pair<Semester, Boolean>>()
val cursor = db.query(query) val cursor = db.query(query)
if (cursor.moveToFirst()) { if (cursor.moveToFirst()) {
@ -153,13 +152,12 @@ class Migration13Test : AbstractMigrationTest() {
diaryName = cursor.getString(3), diaryName = cursor.getString(3),
semesterId = cursor.getInt(4), semesterId = cursor.getInt(4),
semesterName = cursor.getInt(5), semesterName = cursor.getInt(5),
isCurrent = cursor.getInt(6) == 1,
classId = cursor.getInt(7), classId = cursor.getInt(7),
unitId = cursor.getInt(8), unitId = cursor.getInt(8),
schoolYear = cursor.getInt(9), schoolYear = cursor.getInt(9),
start = Converters().timestampToDate(cursor.getLong(10))!!, start = Converters().timestampToDate(cursor.getLong(10))!!,
end = Converters().timestampToDate(cursor.getLong(11))!! end = Converters().timestampToDate(cursor.getLong(11))!!
)) ) to (cursor.getInt(6) == 1))
} while (cursor.moveToNext()) } while (cursor.moveToNext())
} }
return semesters.toList() return semesters.toList()

View File

@ -0,0 +1,29 @@
package io.github.wulkanowy.data.repositories
import io.github.wulkanowy.data.db.entities.Student
import org.threeten.bp.LocalDateTime
fun getStudent(): Student {
return Student(
email = "test",
password = "test123",
schoolSymbol = "23",
scrapperBaseUrl = "fakelog.cf",
loginType = "AUTO",
isCurrent = true,
studentName = "",
schoolShortName = "",
schoolName = "",
studentId = 0,
classId = 1,
symbol = "",
registrationDate = LocalDateTime.now(),
className = "",
loginMode = "API",
certificateKey = "",
privateKey = "",
mobileBaseUrl = "",
userLoginId = 0,
isParent = false
)
}

View File

@ -10,8 +10,8 @@ import org.junit.After
import org.junit.Before import org.junit.Before
import org.junit.Test import org.junit.Test
import org.junit.runner.RunWith import org.junit.runner.RunWith
import org.threeten.bp.LocalDate
import org.threeten.bp.LocalDate.now import org.threeten.bp.LocalDate.now
import org.threeten.bp.LocalDate.of
import kotlin.test.assertEquals import kotlin.test.assertEquals
@RunWith(AndroidJUnit4::class) @RunWith(AndroidJUnit4::class)
@ -35,19 +35,19 @@ class AttendanceLocalTest {
@Test @Test
fun saveAndReadTest() { fun saveAndReadTest() {
attendanceLocal.saveAttendance(listOf( attendanceLocal.saveAttendance(listOf(
Attendance(1, 2, 3, LocalDate.of(2018, 9, 10), 0, "", "", false, false, false, false, false, false, false, SentExcuseStatus.ACCEPTED.name), Attendance(1, 2, 3, of(2018, 9, 10), 0, "", "", false, false, false, false, false, false, false, SentExcuseStatus.ACCEPTED.name),
Attendance(1, 2, 3, LocalDate.of(2018, 9, 14), 0, "", "", false, false, false, false, false, false, false, SentExcuseStatus.WAITING.name), Attendance(1, 2, 3, of(2018, 9, 14), 0, "", "", false, false, false, false, false, false, false, SentExcuseStatus.WAITING.name),
Attendance(1, 2, 3, LocalDate.of(2018, 9, 17), 0, "", "", false, false, false, false, false, false, false, SentExcuseStatus.ACCEPTED.name) Attendance(1, 2, 3, of(2018, 9, 17), 0, "", "", false, false, false, false, false, false, false, SentExcuseStatus.ACCEPTED.name)
)) ))
val attendance = attendanceLocal val attendance = attendanceLocal
.getAttendance(Semester(1, 2, "", 1, 3, 2019, true, now(), now(), 1, 1), .getAttendance(Semester(1, 2, "", 1, 3, 2019, now(), now(), 1, 1),
LocalDate.of(2018, 9, 10), of(2018, 9, 10),
LocalDate.of(2018, 9, 14) of(2018, 9, 14)
) )
.blockingGet() .blockingGet()
assertEquals(2, attendance.size) assertEquals(2, attendance.size)
assertEquals(attendance[0].date, LocalDate.of(2018, 9, 10)) assertEquals(attendance[0].date, of(2018, 9, 10))
assertEquals(attendance[1].date, LocalDate.of(2018, 9, 14)) assertEquals(attendance[1].date, of(2018, 9, 14))
} }
} }

View File

@ -11,6 +11,8 @@ import org.junit.Before
import org.junit.Test import org.junit.Test
import org.junit.runner.RunWith import org.junit.runner.RunWith
import org.threeten.bp.LocalDate import org.threeten.bp.LocalDate
import org.threeten.bp.LocalDate.now
import org.threeten.bp.LocalDate.of
import kotlin.test.assertEquals import kotlin.test.assertEquals
@RunWith(AndroidJUnit4::class) @RunWith(AndroidJUnit4::class)
@ -35,20 +37,20 @@ class CompletedLessonsLocalTest {
@Test @Test
fun saveAndReadTest() { fun saveAndReadTest() {
completedLessonsLocal.saveCompletedLessons(listOf( completedLessonsLocal.saveCompletedLessons(listOf(
getCompletedLesson(LocalDate.of(2018, 9, 10), 1), getCompletedLesson(of(2018, 9, 10), 1),
getCompletedLesson(LocalDate.of(2018, 9, 14), 2), getCompletedLesson(of(2018, 9, 14), 2),
getCompletedLesson(LocalDate.of(2018, 9, 17), 3) getCompletedLesson(of(2018, 9, 17), 3)
)) ))
val completed = completedLessonsLocal val completed = completedLessonsLocal
.getCompletedLessons(Semester(1, 2, "", 1, 3, 2019, true, LocalDate.now(), LocalDate.now(), 1, 1), .getCompletedLessons(Semester(1, 2, "", 1, 3, 2019, now(), now(), 1, 1),
LocalDate.of(2018, 9, 10), of(2018, 9, 10),
LocalDate.of(2018, 9, 14) of(2018, 9, 14)
) )
.blockingGet() .blockingGet()
assertEquals(2, completed.size) assertEquals(2, completed.size)
assertEquals(completed[0].date, LocalDate.of(2018, 9, 10)) assertEquals(completed[0].date, of(2018, 9, 10))
assertEquals(completed[1].date, LocalDate.of(2018, 9, 14)) assertEquals(completed[1].date, of(2018, 9, 14))
} }
private fun getCompletedLesson(date: LocalDate, number: Int): CompletedLesson { private fun getCompletedLesson(date: LocalDate, number: Int): CompletedLesson {

View File

@ -10,7 +10,8 @@ import org.junit.After
import org.junit.Before import org.junit.Before
import org.junit.Test import org.junit.Test
import org.junit.runner.RunWith import org.junit.runner.RunWith
import org.threeten.bp.LocalDate import org.threeten.bp.LocalDate.now
import org.threeten.bp.LocalDate.of
import kotlin.test.assertEquals import kotlin.test.assertEquals
@RunWith(AndroidJUnit4::class) @RunWith(AndroidJUnit4::class)
@ -34,19 +35,19 @@ class ExamLocalTest {
@Test @Test
fun saveAndReadTest() { fun saveAndReadTest() {
examLocal.saveExams(listOf( examLocal.saveExams(listOf(
Exam(1, 2, LocalDate.of(2018, 9, 10), LocalDate.now(), "", "", "", "", "", ""), Exam(1, 2, of(2018, 9, 10), now(), "", "", "", "", "", ""),
Exam(1, 2, LocalDate.of(2018, 9, 14), LocalDate.now(), "", "", "", "", "", ""), Exam(1, 2, of(2018, 9, 14), now(), "", "", "", "", "", ""),
Exam(1, 2, LocalDate.of(2018, 9, 17), LocalDate.now(), "", "", "", "", "", "") Exam(1, 2, of(2018, 9, 17), now(), "", "", "", "", "", "")
)) ))
val exams = examLocal val exams = examLocal
.getExams(Semester(1, 2, "", 1, 3, 2019, true, LocalDate.now(), LocalDate.now(), 1, 1), .getExams(Semester(1, 2, "", 1, 3, 2019, now(), now(), 1, 1),
LocalDate.of(2018, 9, 10), of(2018, 9, 10),
LocalDate.of(2018, 9, 14) of(2018, 9, 14)
) )
.blockingGet() .blockingGet()
assertEquals(2, exams.size) assertEquals(2, exams.size)
assertEquals(exams[0].date, LocalDate.of(2018, 9, 10)) assertEquals(exams[0].date, of(2018, 9, 10))
assertEquals(exams[1].date, LocalDate.of(2018, 9, 14)) assertEquals(exams[1].date, of(2018, 9, 14))
} }
} }

View File

@ -40,7 +40,7 @@ class GradeLocalTest {
createGradeLocal(3, 5.0, LocalDate.of(2019, 2, 28), "", 2) createGradeLocal(3, 5.0, LocalDate.of(2019, 2, 28), "", 2)
)) ))
val semester = Semester(1, 2, "", 2019, 2, 1, true, now(), now(), 1, 1) val semester = Semester(1, 2, "", 2019, 2, 1, now(), now(), 1, 1)
val grades = gradeLocal val grades = gradeLocal
.getGrades(semester) .getGrades(semester)

View File

@ -6,7 +6,6 @@ import androidx.test.core.app.ApplicationProvider.getApplicationContext
import androidx.test.ext.junit.runners.AndroidJUnit4 import androidx.test.ext.junit.runners.AndroidJUnit4
import androidx.test.filters.SdkSuppress import androidx.test.filters.SdkSuppress
import com.github.pwittchen.reactivenetwork.library.rx2.internet.observing.InternetObservingSettings import com.github.pwittchen.reactivenetwork.library.rx2.internet.observing.InternetObservingSettings
import io.github.wulkanowy.data.SdkHelper
import io.github.wulkanowy.data.db.AppDatabase import io.github.wulkanowy.data.db.AppDatabase
import io.github.wulkanowy.data.db.entities.Semester import io.github.wulkanowy.data.db.entities.Semester
import io.github.wulkanowy.data.db.entities.Student import io.github.wulkanowy.data.db.entities.Student
@ -15,9 +14,6 @@ import io.github.wulkanowy.sdk.Sdk
import io.mockk.MockKAnnotations import io.mockk.MockKAnnotations
import io.mockk.every import io.mockk.every
import io.mockk.impl.annotations.MockK import io.mockk.impl.annotations.MockK
import io.mockk.impl.annotations.SpyK
import io.mockk.just
import io.mockk.runs
import io.reactivex.Single import io.reactivex.Single
import org.junit.After import org.junit.After
import org.junit.Before import org.junit.Before

View File

@ -11,7 +11,7 @@ import org.junit.After
import org.junit.Before import org.junit.Before
import org.junit.Test import org.junit.Test
import org.junit.runner.RunWith import org.junit.runner.RunWith
import org.threeten.bp.LocalDate import org.threeten.bp.LocalDate.now
import kotlin.test.assertEquals import kotlin.test.assertEquals
@RunWith(AndroidJUnit4::class) @RunWith(AndroidJUnit4::class)
@ -40,10 +40,7 @@ class GradeStatisticsLocalTest {
getGradeStatistics("Fizyka", 1, 2) getGradeStatistics("Fizyka", 1, 2)
)) ))
val stats = gradeStatisticsLocal.getGradesStatistics( val stats = gradeStatisticsLocal.getGradesStatistics(getSemester(), false, "Matematyka").blockingGet()
Semester(2, 2, "", 2019, 1, 2, true, LocalDate.now(), LocalDate.now(), 1, 1), false,
"Matematyka"
).blockingGet()
assertEquals(1, stats.size) assertEquals(1, stats.size)
assertEquals(stats[0].subject, "Matematyka") assertEquals(stats[0].subject, "Matematyka")
} }
@ -56,12 +53,11 @@ class GradeStatisticsLocalTest {
getGradeStatistics("Fizyka", 1, 2) getGradeStatistics("Fizyka", 1, 2)
)) ))
val stats = gradeStatisticsLocal.getGradesStatistics( val stats = gradeStatisticsLocal.getGradesStatistics(getSemester(), false, "Wszystkie").blockingGet()
Semester(2, 2, "", 2019, 1, 2, true, LocalDate.now(), LocalDate.now(), 1, 1), false, assertEquals(3, stats.size)
"Wszystkie"
).blockingGet()
assertEquals(1, stats.size)
assertEquals(stats[0].subject, "Wszystkie") assertEquals(stats[0].subject, "Wszystkie")
assertEquals(stats[1].subject, "Matematyka")
assertEquals(stats[2].subject, "Chemia")
} }
@Test @Test
@ -72,11 +68,8 @@ class GradeStatisticsLocalTest {
getGradePointsStatistics("Fizyka", 1, 2) getGradePointsStatistics("Fizyka", 1, 2)
)) ))
val stats = gradeStatisticsLocal.getGradesPointsStatistics( val stats = gradeStatisticsLocal.getGradesPointsStatistics(getSemester(), "Matematyka").blockingGet()
Semester(2, 2, "", 2019, 1, 2, true, LocalDate.now(), LocalDate.now(), 1, 1), with(stats[0]) {
"Matematyka"
).blockingGet()
with(stats) {
assertEquals(subject, "Matematyka") assertEquals(subject, "Matematyka")
assertEquals(others, 5.0) assertEquals(others, 5.0)
assertEquals(student, 5.0) assertEquals(student, 5.0)
@ -87,10 +80,7 @@ class GradeStatisticsLocalTest {
fun saveAndRead_subjectEmpty() { fun saveAndRead_subjectEmpty() {
gradeStatisticsLocal.saveGradesPointsStatistics(listOf()) gradeStatisticsLocal.saveGradesPointsStatistics(listOf())
val stats = gradeStatisticsLocal.getGradesPointsStatistics( val stats = gradeStatisticsLocal.getGradesPointsStatistics(getSemester(), "Matematyka").blockingGet()
Semester(2, 2, "", 2019, 1, 2, true, LocalDate.now(), LocalDate.now(), 1, 1),
"Matematyka"
).blockingGet()
assertEquals(null, stats) assertEquals(null, stats)
} }
@ -98,13 +88,14 @@ class GradeStatisticsLocalTest {
fun saveAndRead_allEmpty() { fun saveAndRead_allEmpty() {
gradeStatisticsLocal.saveGradesPointsStatistics(listOf()) gradeStatisticsLocal.saveGradesPointsStatistics(listOf())
val stats = gradeStatisticsLocal.getGradesPointsStatistics( val stats = gradeStatisticsLocal.getGradesPointsStatistics(getSemester(), "Wszystkie").blockingGet()
Semester(2, 2, "", 2019, 1, 2, true, LocalDate.now(), LocalDate.now(), 1, 1),
"Wszystkie"
).blockingGet()
assertEquals(null, stats) assertEquals(null, stats)
} }
private fun getSemester(): Semester {
return Semester(2, 2, "", 2019, 1, 2, now(), now(), 1, 1)
}
private fun getGradeStatistics(subject: String, studentId: Int, semesterId: Int): GradeStatistics { private fun getGradeStatistics(subject: String, studentId: Int, semesterId: Int): GradeStatistics {
return GradeStatistics(studentId, semesterId, subject, 5, 5, false) return GradeStatistics(studentId, semesterId, subject, 5, 5, false)
} }

View File

@ -6,11 +6,13 @@ import androidx.test.ext.junit.runners.AndroidJUnit4
import io.github.wulkanowy.data.db.AppDatabase import io.github.wulkanowy.data.db.AppDatabase
import io.github.wulkanowy.data.db.entities.LuckyNumber import io.github.wulkanowy.data.db.entities.LuckyNumber
import io.github.wulkanowy.data.db.entities.Semester import io.github.wulkanowy.data.db.entities.Semester
import io.github.wulkanowy.data.db.entities.Student
import org.junit.After import org.junit.After
import org.junit.Before import org.junit.Before
import org.junit.Test import org.junit.Test
import org.junit.runner.RunWith import org.junit.runner.RunWith
import org.threeten.bp.LocalDate import org.threeten.bp.LocalDate
import org.threeten.bp.LocalDateTime.now
import kotlin.test.assertEquals import kotlin.test.assertEquals
@RunWith(AndroidJUnit4::class) @RunWith(AndroidJUnit4::class)
@ -36,7 +38,7 @@ class LuckyNumberLocalTest {
fun saveAndReadTest() { fun saveAndReadTest() {
luckyNumberLocal.saveLuckyNumber(LuckyNumber(1, LocalDate.of(2019, 1, 20), 14)) luckyNumberLocal.saveLuckyNumber(LuckyNumber(1, LocalDate.of(2019, 1, 20), 14))
val luckyNumber = luckyNumberLocal.getLuckyNumber(Semester(1, 1, "", 1, 3, 2019, true, LocalDate.now(), LocalDate.now(), 1, 1), val luckyNumber = luckyNumberLocal.getLuckyNumber(Student("", "", "", "", "", "", false, "", "", "", 1, 1, "", "", "", "", "", 1, false, now()),
LocalDate.of(2019, 1, 20) LocalDate.of(2019, 1, 20)
).blockingGet() ).blockingGet()

View File

@ -42,7 +42,7 @@ class RecipientLocalTest {
)) ))
val recipients = recipientLocal.getRecipients( val recipients = recipientLocal.getRecipients(
Student("fakelog.cf", "AUTO", "", "", "", "", false, "", "", "", 1, 0, "", "", "", "", 1, true, LocalDateTime.now()), Student("fakelog.cf", "AUTO", "", "", "", "", false, "", "", "", 1, 0, "", "", "", "", "", 1, true, LocalDateTime.now()),
2, 2,
ReportingUnit(1, 4, "", 0, "", emptyList()) ReportingUnit(1, 4, "", 0, "", emptyList())
).blockingGet() ).blockingGet()

View File

@ -5,13 +5,11 @@ import androidx.room.Room
import androidx.test.core.app.ApplicationProvider import androidx.test.core.app.ApplicationProvider
import androidx.test.ext.junit.runners.AndroidJUnit4 import androidx.test.ext.junit.runners.AndroidJUnit4
import io.github.wulkanowy.data.db.AppDatabase import io.github.wulkanowy.data.db.AppDatabase
import io.github.wulkanowy.data.db.SharedPrefProvider import io.github.wulkanowy.data.repositories.getStudent
import io.github.wulkanowy.data.db.entities.Student
import org.junit.After import org.junit.After
import org.junit.Before import org.junit.Before
import org.junit.Test import org.junit.Test
import org.junit.runner.RunWith import org.junit.runner.RunWith
import org.threeten.bp.LocalDateTime.now
import kotlin.test.assertEquals import kotlin.test.assertEquals
@RunWith(AndroidJUnit4::class) @RunWith(AndroidJUnit4::class)
@ -21,14 +19,13 @@ class StudentLocalTest {
private lateinit var testDb: AppDatabase private lateinit var testDb: AppDatabase
private lateinit var sharedProvider: SharedPrefProvider private val student = getStudent()
@Before @Before
fun createDb() { fun createDb() {
val context = ApplicationProvider.getApplicationContext<Context>() val context = ApplicationProvider.getApplicationContext<Context>()
testDb = Room.inMemoryDatabaseBuilder(context, AppDatabase::class.java) testDb = Room.inMemoryDatabaseBuilder(context, AppDatabase::class.java)
.build() .build()
sharedProvider = SharedPrefProvider(context.getSharedPreferences("TEST", Context.MODE_PRIVATE))
studentLocal = StudentLocal(testDb.studentDao, context) studentLocal = StudentLocal(testDb.studentDao, context)
} }
@ -39,8 +36,7 @@ class StudentLocalTest {
@Test @Test
fun saveAndReadTest() { fun saveAndReadTest() {
studentLocal.saveStudents(listOf(Student(email = "test", password = "test123", schoolSymbol = "23", scrapperBaseUrl = "fakelog.cf", loginType = "AUTO", isCurrent = true, studentName = "", schoolName = "", studentId = 0, classId = 1, symbol = "", registrationDate = now(), className = "", loginMode = "API", certificateKey = "", privateKey = "", mobileBaseUrl = "", userLoginId = 0, isParent = false))) studentLocal.saveStudents(listOf(student)).blockingGet()
.blockingGet()
val student = studentLocal.getCurrentStudent(true).blockingGet() val student = studentLocal.getCurrentStudent(true).blockingGet()
assertEquals("23", student.schoolSymbol) assertEquals("23", student.schoolSymbol)

View File

@ -21,7 +21,7 @@ fun createTimetableLocal(start: LocalDateTime, number: Int, room: String = "", s
teacher = teacher, teacher = teacher,
teacherOld = "", teacherOld = "",
info = "", info = "",
studentPlan = true, isStudentPlan = true,
changes = changes, changes = changes,
canceled = false canceled = false
) )

View File

@ -41,7 +41,7 @@ class TimetableLocalTest {
)) ))
val exams = timetableDb.getTimetable( val exams = timetableDb.getTimetable(
Semester(1, 2, "", 1, 1, 2019, true, LocalDate.now(), LocalDate.now(), 1, 1), Semester(1, 2, "", 1, 1, 2019, LocalDate.now(), LocalDate.now(), 1, 1),
LocalDate.of(2018, 9, 10), LocalDate.of(2018, 9, 10),
LocalDate.of(2018, 9, 14) LocalDate.of(2018, 9, 14)
).blockingGet() ).blockingGet()

View File

@ -9,6 +9,7 @@ import com.github.pwittchen.reactivenetwork.library.rx2.internet.observing.Inter
import io.github.wulkanowy.data.db.AppDatabase import io.github.wulkanowy.data.db.AppDatabase
import io.github.wulkanowy.data.db.entities.Semester import io.github.wulkanowy.data.db.entities.Semester
import io.github.wulkanowy.data.repositories.TestInternetObservingStrategy import io.github.wulkanowy.data.repositories.TestInternetObservingStrategy
import io.github.wulkanowy.data.repositories.getStudent
import io.github.wulkanowy.sdk.Sdk import io.github.wulkanowy.sdk.Sdk
import io.mockk.MockKAnnotations import io.mockk.MockKAnnotations
import io.mockk.every import io.mockk.every
@ -33,6 +34,8 @@ class TimetableRepositoryTest {
.strategy(TestInternetObservingStrategy()) .strategy(TestInternetObservingStrategy())
.build() .build()
private val student = getStudent()
@MockK @MockK
private lateinit var semesterMock: Semester private lateinit var semesterMock: Semester
@ -78,7 +81,7 @@ class TimetableRepositoryTest {
)) ))
val lessons = TimetableRepository(settings, timetableLocal, timetableRemote) val lessons = TimetableRepository(settings, timetableLocal, timetableRemote)
.getTimetable(semesterMock, LocalDate.of(2019, 3, 5), LocalDate.of(2019, 3, 5), true) .getTimetable(student, semesterMock, LocalDate.of(2019, 3, 5), LocalDate.of(2019, 3, 5), true)
.blockingGet() .blockingGet()
assertEquals(4, lessons.size) assertEquals(4, lessons.size)
@ -124,7 +127,7 @@ class TimetableRepositoryTest {
)) ))
val lessons = TimetableRepository(settings, timetableLocal, timetableRemote) val lessons = TimetableRepository(settings, timetableLocal, timetableRemote)
.getTimetable(semesterMock, LocalDate.of(2019, 12, 23), LocalDate.of(2019, 12, 25), true) .getTimetable(student, semesterMock, LocalDate.of(2019, 12, 23), LocalDate.of(2019, 12, 25), true)
.blockingGet() .blockingGet()
assertEquals(12, lessons.size) assertEquals(12, lessons.size)

View File

@ -0,0 +1,4 @@
<resources xmlns:tools="http://schemas.android.com/tools" tools:ignore="MissingTranslation">
<bool name="pref_default_notification_debug">true</bool>
</resources>

View File

@ -5,13 +5,12 @@ package io.github.wulkanowy.utils
import android.content.Context import android.content.Context
import timber.log.Timber import timber.log.Timber
fun initCrashlytics(context: Context, appInfo: AppInfo) { fun initCrashlytics(context: Context, appInfo: AppInfo) {}
// do nothing
open class TimberTreeNoOp : Timber.Tree() {
override fun log(priority: Int, tag: String?, message: String, t: Throwable?) {}
} }
class CrashlyticsTree : Timber.Tree() { class CrashlyticsTree : TimberTreeNoOp()
override fun log(priority: Int, tag: String?, message: String, t: Throwable?) { class CrashlyticsExceptionTree : TimberTreeNoOp()
// do nothing
}
}

View File

@ -22,7 +22,8 @@
<activity <activity
android:name=".ui.modules.splash.SplashActivity" android:name=".ui.modules.splash.SplashActivity"
android:screenOrientation="portrait" android:screenOrientation="portrait"
android:theme="@style/WulkanowyTheme.SplashScreen"> android:theme="@style/WulkanowyTheme.SplashScreen"
tools:ignore="LockedOrientationActivity">
<intent-filter> <intent-filter>
<action android:name="android.intent.action.MAIN" /> <action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" /> <category android:name="android.intent.category.LAUNCHER" />
@ -43,8 +44,8 @@
android:name=".ui.modules.message.send.SendMessageActivity" android:name=".ui.modules.message.send.SendMessageActivity"
android:configChanges="orientation|screenSize" android:configChanges="orientation|screenSize"
android:label="@string/send_message_title" android:label="@string/send_message_title"
android:windowSoftInputMode="adjustResize" android:theme="@style/WulkanowyTheme.NoActionBar"
android:theme="@style/WulkanowyTheme.NoActionBar" /> android:windowSoftInputMode="adjustResize" />
<activity <activity
android:name=".ui.modules.timetablewidget.TimetableWidgetConfigureActivity" android:name=".ui.modules.timetablewidget.TimetableWidgetConfigureActivity"
android:excludeFromRecents="true" android:excludeFromRecents="true"
@ -96,11 +97,29 @@
android:exported="false" android:exported="false"
tools:node="remove" /> tools:node="remove" />
<provider
android:name="androidx.core.content.FileProvider"
android:authorities="${applicationId}.fileprovider"
android:exported="false"
android:grantUriPermissions="true">
<meta-data
android:name="android.support.FILE_PROVIDER_PATHS"
android:resource="@xml/provider_paths" />
</provider>
<meta-data <meta-data
android:name="io.fabric.ApiKey" android:name="io.fabric.ApiKey"
android:value="${fabric_api_key}" /> android:value="${fabric_api_key}" />
<meta-data <meta-data
android:name="firebase_crashlytics_collection_enabled" android:name="firebase_crashlytics_collection_enabled"
android:value="${crashlytics_enabled}" /> android:value="${crashlytics_enabled}" />
<meta-data
android:name="com.google.firebase.messaging.default_notification_icon"
android:resource="@drawable/ic_stat_push" />
<meta-data
android:name="com.google.firebase.messaging.default_notification_channel_id"
android:value="push_channel" />
</application> </application>
</manifest> </manifest>

View File

@ -20,7 +20,7 @@
"githubUsername": "doteq" "githubUsername": "doteq"
}, },
{ {
"displayName": "Pavuloff", "displayName": "Paweł Krzyś",
"githubUsername": "pavuloff" "githubUsername": "pavuloff"
}, },
{ {
@ -30,5 +30,9 @@
{ {
"displayName": "Dinolek", "displayName": "Dinolek",
"githubUsername": "Dinolek" "githubUsername": "Dinolek"
},
{
"displayName": "Mateusz Idziejczak",
"githubUsername": "PanTajemnic"
} }
] ]

View File

@ -1,6 +1,7 @@
package io.github.wulkanowy package io.github.wulkanowy
import android.content.Context import android.content.Context
import android.util.Log.DEBUG
import android.util.Log.INFO import android.util.Log.INFO
import android.util.Log.VERBOSE import android.util.Log.VERBOSE
import androidx.multidex.MultiDex import androidx.multidex.MultiDex
@ -11,11 +12,13 @@ import dagger.android.AndroidInjector
import dagger.android.support.DaggerApplication import dagger.android.support.DaggerApplication
import eu.davidea.flexibleadapter.FlexibleAdapter import eu.davidea.flexibleadapter.FlexibleAdapter
import eu.davidea.flexibleadapter.utils.Log import eu.davidea.flexibleadapter.utils.Log
import fr.bipi.tressence.file.FileLoggerTree
import io.github.wulkanowy.di.DaggerAppComponent import io.github.wulkanowy.di.DaggerAppComponent
import io.github.wulkanowy.services.sync.SyncWorkerFactory import io.github.wulkanowy.services.sync.SyncWorkerFactory
import io.github.wulkanowy.ui.base.ThemeManager import io.github.wulkanowy.ui.base.ThemeManager
import io.github.wulkanowy.utils.ActivityLifecycleLogger import io.github.wulkanowy.utils.ActivityLifecycleLogger
import io.github.wulkanowy.utils.AppInfo import io.github.wulkanowy.utils.AppInfo
import io.github.wulkanowy.utils.CrashlyticsExceptionTree
import io.github.wulkanowy.utils.CrashlyticsTree import io.github.wulkanowy.utils.CrashlyticsTree
import io.github.wulkanowy.utils.DebugLogTree import io.github.wulkanowy.utils.DebugLogTree
import io.github.wulkanowy.utils.initCrashlytics import io.github.wulkanowy.utils.initCrashlytics
@ -54,9 +57,17 @@ class WulkanowyApp : DaggerApplication(), Configuration.Provider {
private fun initLogging() { private fun initLogging() {
if (appInfo.isDebug) { if (appInfo.isDebug) {
Timber.plant(DebugLogTree())
FlexibleAdapter.enableLogs(Log.Level.DEBUG) FlexibleAdapter.enableLogs(Log.Level.DEBUG)
Timber.plant(DebugLogTree())
Timber.plant(FileLoggerTree.Builder()
.withFileName("wulkanowy.%g.log")
.withDirName(applicationContext.filesDir.absolutePath)
.withFileLimit(10)
.withMinPriority(DEBUG)
.build()
)
} else { } else {
Timber.plant(CrashlyticsExceptionTree())
Timber.plant(CrashlyticsTree()) Timber.plant(CrashlyticsTree())
} }
registerActivityLifecycleCallbacks(ActivityLifecycleLogger()) registerActivityLifecycleCallbacks(ActivityLifecycleLogger())

View File

@ -7,9 +7,9 @@ import android.content.res.Resources
import androidx.preference.PreferenceManager import androidx.preference.PreferenceManager
import com.github.pwittchen.reactivenetwork.library.rx2.internet.observing.InternetObservingSettings import com.github.pwittchen.reactivenetwork.library.rx2.internet.observing.InternetObservingSettings
import com.github.pwittchen.reactivenetwork.library.rx2.internet.observing.strategy.WalledGardenInternetObservingStrategy import com.github.pwittchen.reactivenetwork.library.rx2.internet.observing.strategy.WalledGardenInternetObservingStrategy
import com.readystatesoftware.chuck.api.ChuckCollector import com.chuckerteam.chucker.api.ChuckerCollector
import com.readystatesoftware.chuck.api.ChuckInterceptor import com.chuckerteam.chucker.api.ChuckerInterceptor
import com.readystatesoftware.chuck.api.RetentionManager import com.chuckerteam.chucker.api.RetentionManager
import dagger.Module import dagger.Module
import dagger.Provides import dagger.Provides
import io.github.wulkanowy.data.db.AppDatabase import io.github.wulkanowy.data.db.AppDatabase
@ -32,23 +32,25 @@ internal class RepositoryModule {
@Singleton @Singleton
@Provides @Provides
fun provideSdk(chuckCollector: ChuckCollector, context: Context): Sdk { fun provideSdk(chuckerCollector: ChuckerCollector, context: Context): Sdk {
return Sdk().apply { return Sdk().apply {
androidVersion = android.os.Build.VERSION.RELEASE androidVersion = android.os.Build.VERSION.RELEASE
buildTag = android.os.Build.MODEL buildTag = android.os.Build.MODEL
setSimpleHttpLogger { Timber.d(it) } setSimpleHttpLogger { Timber.d(it) }
// for debug only // for debug only
addInterceptor(ChuckInterceptor(context, chuckCollector).maxContentLength(250000L), true) addInterceptor(ChuckerInterceptor(context, chuckerCollector), true)
} }
} }
@Singleton @Singleton
@Provides @Provides
fun provideChuckCollector(context: Context, prefRepository: PreferencesRepository): ChuckCollector { fun provideChuckerCollector(context: Context, prefRepository: PreferencesRepository): ChuckerCollector {
return ChuckCollector(context) return ChuckerCollector(
.showNotification(prefRepository.isDebugNotificationEnable) context = context,
.retentionManager(RetentionManager(context, ChuckCollector.Period.ONE_HOUR)) showNotification = prefRepository.isDebugNotificationEnable,
retentionPeriod = RetentionManager.Period.ONE_HOUR
)
} }
@Singleton @Singleton
@ -95,6 +97,10 @@ internal class RepositoryModule {
@Provides @Provides
fun provideMessagesDao(database: AppDatabase) = database.messagesDao fun provideMessagesDao(database: AppDatabase) = database.messagesDao
@Singleton
@Provides
fun provideMessageAttachmentsDao(database: AppDatabase) = database.messageAttachmentDao
@Singleton @Singleton
@Provides @Provides
fun provideExamDao(database: AppDatabase) = database.examsDao fun provideExamDao(database: AppDatabase) = database.examsDao

View File

@ -1,30 +0,0 @@
package io.github.wulkanowy.data
import io.github.wulkanowy.data.db.entities.Student
import io.github.wulkanowy.sdk.Sdk
import javax.inject.Inject
class SdkHelper @Inject constructor(private val sdk: Sdk) {
fun init(student: Student) {
sdk.apply {
email = student.email
password = student.password
symbol = student.symbol
schoolSymbol = student.schoolSymbol
studentId = student.studentId
classId = student.classId
if (Sdk.Mode.valueOf(student.loginMode) != Sdk.Mode.API) {
scrapperBaseUrl = student.scrapperBaseUrl
loginType = Sdk.ScrapperLoginType.valueOf(student.loginType)
}
loginId = student.userLoginId
mode = Sdk.Mode.valueOf(student.loginMode)
mobileBaseUrl = student.mobileBaseUrl
certKey = student.certificateKey
privateKey = student.privateKey
}
}
}

View File

@ -17,6 +17,7 @@ import io.github.wulkanowy.data.db.dao.GradeStatisticsDao
import io.github.wulkanowy.data.db.dao.GradeSummaryDao import io.github.wulkanowy.data.db.dao.GradeSummaryDao
import io.github.wulkanowy.data.db.dao.HomeworkDao import io.github.wulkanowy.data.db.dao.HomeworkDao
import io.github.wulkanowy.data.db.dao.LuckyNumberDao import io.github.wulkanowy.data.db.dao.LuckyNumberDao
import io.github.wulkanowy.data.db.dao.MessageAttachmentDao
import io.github.wulkanowy.data.db.dao.MessagesDao import io.github.wulkanowy.data.db.dao.MessagesDao
import io.github.wulkanowy.data.db.dao.MobileDeviceDao import io.github.wulkanowy.data.db.dao.MobileDeviceDao
import io.github.wulkanowy.data.db.dao.NoteDao import io.github.wulkanowy.data.db.dao.NoteDao
@ -39,6 +40,7 @@ import io.github.wulkanowy.data.db.entities.GradeSummary
import io.github.wulkanowy.data.db.entities.Homework import io.github.wulkanowy.data.db.entities.Homework
import io.github.wulkanowy.data.db.entities.LuckyNumber import io.github.wulkanowy.data.db.entities.LuckyNumber
import io.github.wulkanowy.data.db.entities.Message import io.github.wulkanowy.data.db.entities.Message
import io.github.wulkanowy.data.db.entities.MessageAttachment
import io.github.wulkanowy.data.db.entities.MobileDevice import io.github.wulkanowy.data.db.entities.MobileDevice
import io.github.wulkanowy.data.db.entities.Note import io.github.wulkanowy.data.db.entities.Note
import io.github.wulkanowy.data.db.entities.Recipient import io.github.wulkanowy.data.db.entities.Recipient
@ -62,6 +64,10 @@ import io.github.wulkanowy.data.db.migrations.Migration19
import io.github.wulkanowy.data.db.migrations.Migration2 import io.github.wulkanowy.data.db.migrations.Migration2
import io.github.wulkanowy.data.db.migrations.Migration20 import io.github.wulkanowy.data.db.migrations.Migration20
import io.github.wulkanowy.data.db.migrations.Migration21 import io.github.wulkanowy.data.db.migrations.Migration21
import io.github.wulkanowy.data.db.migrations.Migration22
import io.github.wulkanowy.data.db.migrations.Migration23
import io.github.wulkanowy.data.db.migrations.Migration24
import io.github.wulkanowy.data.db.migrations.Migration25
import io.github.wulkanowy.data.db.migrations.Migration3 import io.github.wulkanowy.data.db.migrations.Migration3
import io.github.wulkanowy.data.db.migrations.Migration4 import io.github.wulkanowy.data.db.migrations.Migration4
import io.github.wulkanowy.data.db.migrations.Migration5 import io.github.wulkanowy.data.db.migrations.Migration5
@ -85,6 +91,7 @@ import javax.inject.Singleton
GradeStatistics::class, GradeStatistics::class,
GradePointsStatistics::class, GradePointsStatistics::class,
Message::class, Message::class,
MessageAttachment::class,
Note::class, Note::class,
Homework::class, Homework::class,
Subject::class, Subject::class,
@ -103,7 +110,7 @@ import javax.inject.Singleton
abstract class AppDatabase : RoomDatabase() { abstract class AppDatabase : RoomDatabase() {
companion object { companion object {
const val VERSION_SCHEMA = 21 const val VERSION_SCHEMA = 25
fun getMigrations(sharedPrefProvider: SharedPrefProvider): Array<Migration> { fun getMigrations(sharedPrefProvider: SharedPrefProvider): Array<Migration> {
return arrayOf( return arrayOf(
@ -126,7 +133,11 @@ abstract class AppDatabase : RoomDatabase() {
Migration18(), Migration18(),
Migration19(sharedPrefProvider), Migration19(sharedPrefProvider),
Migration20(), Migration20(),
Migration21() Migration21(),
Migration22(),
Migration23(),
Migration24(),
Migration25()
) )
} }
@ -162,6 +173,8 @@ abstract class AppDatabase : RoomDatabase() {
abstract val messagesDao: MessagesDao abstract val messagesDao: MessagesDao
abstract val messageAttachmentDao: MessageAttachmentDao
abstract val noteDao: NoteDao abstract val noteDao: NoteDao
abstract val homeworkDao: HomeworkDao abstract val homeworkDao: HomeworkDao

View File

@ -48,4 +48,14 @@ class Converters {
fun gsonToIntList(value: String): List<Int> { fun gsonToIntList(value: String): List<Int> {
return Gson().fromJson(value, object : TypeToken<List<Int>>() {}.type) return Gson().fromJson(value, object : TypeToken<List<Int>>() {}.type)
} }
@TypeConverter
fun stringPairListToGson(list: List<Pair<String, String>>): String {
return Gson().toJson(list)
}
@TypeConverter
fun gsonToStringPairList(value: String): List<Pair<String, String>> {
return Gson().fromJson(value, object : TypeToken<List<Pair<String, String>>>() {}.type)
}
} }

View File

@ -11,7 +11,7 @@ import javax.inject.Singleton
interface GradePointsStatisticsDao : BaseDao<GradePointsStatistics> { interface GradePointsStatisticsDao : BaseDao<GradePointsStatistics> {
@Query("SELECT * FROM GradesPointsStatistics WHERE student_id = :studentId AND semester_id = :semesterId AND subject = :subjectName") @Query("SELECT * FROM GradesPointsStatistics WHERE student_id = :studentId AND semester_id = :semesterId AND subject = :subjectName")
fun loadSubject(semesterId: Int, studentId: Int, subjectName: String): Maybe<GradePointsStatistics> fun loadSubject(semesterId: Int, studentId: Int, subjectName: String): Maybe<List<GradePointsStatistics>>
@Query("SELECT * FROM GradesPointsStatistics WHERE student_id = :studentId AND semester_id = :semesterId") @Query("SELECT * FROM GradesPointsStatistics WHERE student_id = :studentId AND semester_id = :semesterId")
fun loadAll(semesterId: Int, studentId: Int): Maybe<List<GradePointsStatistics>> fun loadAll(semesterId: Int, studentId: Int): Maybe<List<GradePointsStatistics>>

View File

@ -0,0 +1,13 @@
package io.github.wulkanowy.data.db.dao
import androidx.room.Dao
import androidx.room.Insert
import androidx.room.OnConflictStrategy
import io.github.wulkanowy.data.db.entities.MessageAttachment
@Dao
interface MessageAttachmentDao : BaseDao<MessageAttachment> {
@Insert(onConflict = OnConflictStrategy.REPLACE)
fun insertAttachments(items: List<MessageAttachment>): List<Long>
}

View File

@ -2,18 +2,22 @@ package io.github.wulkanowy.data.db.dao
import androidx.room.Dao import androidx.room.Dao
import androidx.room.Query import androidx.room.Query
import androidx.room.Transaction
import io.github.wulkanowy.data.db.entities.Message import io.github.wulkanowy.data.db.entities.Message
import io.github.wulkanowy.data.db.entities.MessageWithAttachment
import io.reactivex.Maybe import io.reactivex.Maybe
import io.reactivex.Single
@Dao @Dao
interface MessagesDao : BaseDao<Message> { interface MessagesDao : BaseDao<Message> {
@Transaction
@Query("SELECT * FROM Messages WHERE student_id = :studentId AND message_id = :messageId")
fun loadMessageWithAttachment(studentId: Int, messageId: Int): Single<MessageWithAttachment>
@Query("SELECT * FROM Messages WHERE student_id = :studentId AND folder_id = :folder AND removed = 0 ORDER BY date DESC") @Query("SELECT * FROM Messages WHERE student_id = :studentId AND folder_id = :folder AND removed = 0 ORDER BY date DESC")
fun loadAll(studentId: Int, folder: Int): Maybe<List<Message>> fun loadAll(studentId: Int, folder: Int): Maybe<List<Message>>
@Query("SELECT * FROM Messages WHERE id = :id")
fun load(id: Long): Maybe<Message>
@Query("SELECT * FROM Messages WHERE student_id = :studentId AND removed = 1 ORDER BY date DESC") @Query("SELECT * FROM Messages WHERE student_id = :studentId AND removed = 1 ORDER BY date DESC")
fun loadDeleted(studentId: Int): Maybe<List<Message>> fun loadDeleted(studentId: Int): Maybe<List<Message>>
} }

View File

@ -22,6 +22,9 @@ interface StudentDao {
@Query("SELECT * FROM Students WHERE is_current = 1") @Query("SELECT * FROM Students WHERE is_current = 1")
fun loadCurrent(): Maybe<Student> fun loadCurrent(): Maybe<Student>
@Query("SELECT * FROM Students WHERE id = :id")
fun loadById(id: Int): Maybe<Student>
@Query("SELECT * FROM Students") @Query("SELECT * FROM Students")
fun loadAll(): Maybe<List<Student>> fun loadAll(): Maybe<List<Student>>

View File

@ -27,10 +27,14 @@ data class Homework(
val teacher: String, val teacher: String,
@ColumnInfo(name = "teacher_symbol") @ColumnInfo(name = "teacher_symbol")
val teacherSymbol: String val teacherSymbol: String,
val attachments: List<Pair<String, String>>
) : Serializable { ) : Serializable {
@PrimaryKey(autoGenerate = true) @PrimaryKey(autoGenerate = true)
var id: Long = 0 var id: Long = 0
@ColumnInfo(name = "is_done")
var isDone: Boolean = false
} }

View File

@ -44,7 +44,10 @@ data class Message(
@ColumnInfo(name = "read_by") @ColumnInfo(name = "read_by")
val readBy: Int, val readBy: Int,
val removed: Boolean val removed: Boolean,
@ColumnInfo(name = "has_attachments")
val hasAttachments: Boolean
) : Serializable { ) : Serializable {
@PrimaryKey(autoGenerate = true) @PrimaryKey(autoGenerate = true)

View File

@ -0,0 +1,26 @@
package io.github.wulkanowy.data.db.entities
import androidx.room.ColumnInfo
import androidx.room.Entity
import androidx.room.PrimaryKey
import java.io.Serializable
@Entity(tableName = "MessageAttachments")
data class MessageAttachment(
@PrimaryKey
@ColumnInfo(name = "real_id")
val realId: Int,
@ColumnInfo(name = "message_id")
val messageId: Int,
@ColumnInfo(name = "one_drive_id")
val oneDriveId: String,
@ColumnInfo(name = "url")
val url: String,
@ColumnInfo(name = "filename")
val filename: String
) : Serializable

View File

@ -0,0 +1,12 @@
package io.github.wulkanowy.data.db.entities
import androidx.room.Embedded
import androidx.room.Relation
data class MessageWithAttachment(
@Embedded
val message: Message,
@Relation(parentColumn = "message_id", entityColumn = "message_id")
val attachments: List<MessageAttachment>
)

View File

@ -16,8 +16,19 @@ data class Note(
val teacher: String, val teacher: String,
@ColumnInfo(name = "teacher_symbol")
val teacherSymbol: String,
val category: String, val category: String,
@ColumnInfo(name = "category_type")
val categoryType: Int,
@ColumnInfo(name = "is_points_show")
val isPointsShow: Boolean,
val points: Int,
val content: String val content: String
) : Serializable { ) : Serializable {

View File

@ -27,9 +27,6 @@ data class Semester(
@ColumnInfo(name = "semester_name") @ColumnInfo(name = "semester_name")
val semesterName: Int, val semesterName: Int,
@ColumnInfo(name = "is_current")
val isCurrent: Boolean,
val start: LocalDate, val start: LocalDate,
val end: LocalDate, val end: LocalDate,
@ -43,4 +40,8 @@ data class Semester(
@PrimaryKey(autoGenerate = true) @PrimaryKey(autoGenerate = true)
var id: Long = 0 var id: Long = 0
@ColumnInfo(name = "is_current")
var current: Boolean = false
} }

View File

@ -49,6 +49,9 @@ data class Student(
@ColumnInfo(name = "school_id") @ColumnInfo(name = "school_id")
val schoolSymbol: String, val schoolSymbol: String,
@ColumnInfo(name ="school_short")
val schoolShortName: String,
@ColumnInfo(name = "school_name") @ColumnInfo(name = "school_name")
val schoolName: String, val schoolName: String,

View File

@ -41,7 +41,7 @@ data class Timetable(
val info: String, val info: String,
@ColumnInfo(name = "student_plan") @ColumnInfo(name = "student_plan")
val studentPlan: Boolean, val isStudentPlan: Boolean,
val changes: Boolean, val changes: Boolean,

View File

@ -0,0 +1,11 @@
package io.github.wulkanowy.data.db.migrations
import androidx.room.migration.Migration
import androidx.sqlite.db.SupportSQLiteDatabase
class Migration22 : Migration(21, 22) {
override fun migrate(database: SupportSQLiteDatabase) {
database.execSQL("ALTER TABLE Students ADD COLUMN school_short TEXT NOT NULL DEFAULT ''")
}
}

View File

@ -0,0 +1,14 @@
package io.github.wulkanowy.data.db.migrations
import androidx.room.migration.Migration
import androidx.sqlite.db.SupportSQLiteDatabase
class Migration23 : Migration(22, 23) {
override fun migrate(database: SupportSQLiteDatabase) {
database.execSQL("ALTER TABLE Notes ADD COLUMN teacher_symbol TEXT NOT NULL DEFAULT ''")
database.execSQL("ALTER TABLE Notes ADD COLUMN category_type INTEGER NOT NULL DEFAULT 0")
database.execSQL("ALTER TABLE Notes ADD COLUMN is_points_show INTEGER NOT NULL DEFAULT 0")
database.execSQL("ALTER TABLE Notes ADD COLUMN points INTEGER NOT NULL DEFAULT 0")
}
}

View File

@ -0,0 +1,21 @@
package io.github.wulkanowy.data.db.migrations
import androidx.room.migration.Migration
import androidx.sqlite.db.SupportSQLiteDatabase
class Migration24 : Migration(23, 24) {
override fun migrate(database: SupportSQLiteDatabase) {
database.execSQL("ALTER TABLE Messages ADD COLUMN has_attachments INTEGER NOT NULL DEFAULT 0")
database.execSQL("""
CREATE TABLE IF NOT EXISTS MessageAttachments (
real_id INTEGER NOT NULL,
message_id INTEGER NOT NULL,
one_drive_id TEXT NOT NULL,
url TEXT NOT NULL,
filename TEXT NOT NULL,
PRIMARY KEY(real_id)
)
""")
}
}

View File

@ -0,0 +1,12 @@
package io.github.wulkanowy.data.db.migrations
import androidx.room.migration.Migration
import androidx.sqlite.db.SupportSQLiteDatabase
class Migration25 : Migration(24, 25) {
override fun migrate(database: SupportSQLiteDatabase) {
database.execSQL("ALTER TABLE Homework ADD COLUMN is_done INTEGER NOT NULL DEFAULT 0")
database.execSQL("ALTER TABLE Homework ADD COLUMN attachments TEXT NOT NULL DEFAULT \"[]\"")
}
}

View File

@ -0,0 +1,14 @@
package io.github.wulkanowy.data.pojos
import io.github.wulkanowy.data.db.entities.GradePointsStatistics
import io.github.wulkanowy.data.db.entities.GradeStatistics
import io.github.wulkanowy.ui.modules.grade.statistics.ViewType
data class GradeStatisticsItem(
val type: ViewType,
val partial: List<GradeStatistics>,
val points: GradePointsStatistics?
)

View File

@ -12,7 +12,7 @@ class AppCreatorRepository @Inject constructor(private val assets: AssetManager)
fun getAppCreators(): Single<List<AppCreator>> { fun getAppCreators(): Single<List<AppCreator>> {
return Single.fromCallable<List<AppCreator>> { return Single.fromCallable<List<AppCreator>> {
Gson().fromJson( Gson().fromJson(
assets.open("creators.json").bufferedReader().use { it.readText() }, assets.open("contributors.json").bufferedReader().use { it.readText() },
Array<AppCreator>::class.java Array<AppCreator>::class.java
).toList() ).toList()
} }

View File

@ -2,8 +2,10 @@ package io.github.wulkanowy.data.repositories.attendance
import io.github.wulkanowy.data.db.entities.Attendance import io.github.wulkanowy.data.db.entities.Attendance
import io.github.wulkanowy.data.db.entities.Semester import io.github.wulkanowy.data.db.entities.Semester
import io.github.wulkanowy.data.db.entities.Student
import io.github.wulkanowy.sdk.Sdk import io.github.wulkanowy.sdk.Sdk
import io.github.wulkanowy.sdk.pojo.Absent import io.github.wulkanowy.sdk.pojo.Absent
import io.github.wulkanowy.utils.init
import io.reactivex.Single import io.reactivex.Single
import org.threeten.bp.LocalDate import org.threeten.bp.LocalDate
import org.threeten.bp.LocalDateTime import org.threeten.bp.LocalDateTime
@ -14,8 +16,9 @@ import javax.inject.Singleton
@Singleton @Singleton
class AttendanceRemote @Inject constructor(private val sdk: Sdk) { class AttendanceRemote @Inject constructor(private val sdk: Sdk) {
fun getAttendance(semester: Semester, startDate: LocalDate, endDate: LocalDate): Single<List<Attendance>> { fun getAttendance(student: Student, semester: Semester, startDate: LocalDate, endDate: LocalDate): Single<List<Attendance>> {
return sdk.switchDiary(semester.diaryId, semester.schoolYear).getAttendance(startDate, endDate, semester.semesterId) return sdk.init(student).switchDiary(semester.diaryId, semester.schoolYear)
.getAttendance(startDate, endDate, semester.semesterId)
.map { attendance -> .map { attendance ->
attendance.map { attendance.map {
Attendance( Attendance(
@ -39,8 +42,8 @@ class AttendanceRemote @Inject constructor(private val sdk: Sdk) {
} }
} }
fun excuseAbsence(semester: Semester, absenceList: List<Attendance>, reason: String?): Single<Boolean> { fun excuseAbsence(student: Student, semester: Semester, absenceList: List<Attendance>, reason: String?): Single<Boolean> {
return sdk.switchDiary(semester.diaryId, semester.schoolYear).excuseForAbsence(absenceList.map { attendance -> return sdk.init(student).switchDiary(semester.diaryId, semester.schoolYear).excuseForAbsence(absenceList.map { attendance ->
Absent( Absent(
date = LocalDateTime.of(attendance.date, LocalTime.of(0, 0)), date = LocalDateTime.of(attendance.date, LocalTime.of(0, 0)),
timeId = attendance.timeId timeId = attendance.timeId

View File

@ -4,6 +4,7 @@ import com.github.pwittchen.reactivenetwork.library.rx2.ReactiveNetwork
import com.github.pwittchen.reactivenetwork.library.rx2.internet.observing.InternetObservingSettings import com.github.pwittchen.reactivenetwork.library.rx2.internet.observing.InternetObservingSettings
import io.github.wulkanowy.data.db.entities.Attendance import io.github.wulkanowy.data.db.entities.Attendance
import io.github.wulkanowy.data.db.entities.Semester import io.github.wulkanowy.data.db.entities.Semester
import io.github.wulkanowy.data.db.entities.Student
import io.github.wulkanowy.utils.friday import io.github.wulkanowy.utils.friday
import io.github.wulkanowy.utils.monday import io.github.wulkanowy.utils.monday
import io.github.wulkanowy.utils.uniqueSubtract import io.github.wulkanowy.utils.uniqueSubtract
@ -20,29 +21,25 @@ class AttendanceRepository @Inject constructor(
private val remote: AttendanceRemote private val remote: AttendanceRemote
) { ) {
fun getAttendance(semester: Semester, startDate: LocalDate, endDate: LocalDate, forceRefresh: Boolean) fun getAttendance(student: Student, semester: Semester, start: LocalDate, end: LocalDate, forceRefresh: Boolean): Single<List<Attendance>> {
: Single<List<Attendance>> { return local.getAttendance(semester, start.monday, end.friday).filter { !forceRefresh }
return Single.fromCallable { startDate.monday to endDate.friday }
.flatMap { dates ->
local.getAttendance(semester, dates.first, dates.second).filter { !forceRefresh }
.switchIfEmpty(ReactiveNetwork.checkInternetConnectivity(settings).flatMap { .switchIfEmpty(ReactiveNetwork.checkInternetConnectivity(settings).flatMap {
if (it) remote.getAttendance(semester, dates.first, dates.second) if (it) remote.getAttendance(student, semester, start.monday, end.friday)
else Single.error(UnknownHostException()) else Single.error(UnknownHostException())
}.flatMap { newAttendance -> }.flatMap { newAttendance ->
local.getAttendance(semester, dates.first, dates.second) local.getAttendance(semester, start.monday, end.friday)
.toSingle(emptyList()) .toSingle(emptyList())
.doOnSuccess { oldAttendance -> .doOnSuccess { oldAttendance ->
local.deleteAttendance(oldAttendance.uniqueSubtract(newAttendance)) local.deleteAttendance(oldAttendance.uniqueSubtract(newAttendance))
local.saveAttendance(newAttendance.uniqueSubtract(oldAttendance)) local.saveAttendance(newAttendance.uniqueSubtract(oldAttendance))
} }
}.flatMap { }.flatMap {
local.getAttendance(semester, dates.first, dates.second) local.getAttendance(semester, start.monday, end.friday)
.toSingle(emptyList()) .toSingle(emptyList())
}).map { list -> list.filter { it.date in startDate..endDate } } }).map { list -> list.filter { it.date in start..end } }
}
} }
fun excuseForAbsence(semester: Semester, attendanceList: List<Attendance>, reason: String? = null): Single<Boolean> { fun excuseForAbsence(student: Student, semester: Semester, attendanceList: List<Attendance>, reason: String? = null): Single<Boolean> {
return remote.excuseAbsence(semester, attendanceList, reason) return remote.excuseAbsence(student, semester, attendanceList, reason)
} }
} }

View File

@ -2,7 +2,9 @@ package io.github.wulkanowy.data.repositories.attendancesummary
import io.github.wulkanowy.data.db.entities.AttendanceSummary import io.github.wulkanowy.data.db.entities.AttendanceSummary
import io.github.wulkanowy.data.db.entities.Semester import io.github.wulkanowy.data.db.entities.Semester
import io.github.wulkanowy.data.db.entities.Student
import io.github.wulkanowy.sdk.Sdk import io.github.wulkanowy.sdk.Sdk
import io.github.wulkanowy.utils.init
import io.reactivex.Single import io.reactivex.Single
import javax.inject.Inject import javax.inject.Inject
import javax.inject.Singleton import javax.inject.Singleton
@ -10,8 +12,9 @@ import javax.inject.Singleton
@Singleton @Singleton
class AttendanceSummaryRemote @Inject constructor(private val sdk: Sdk) { class AttendanceSummaryRemote @Inject constructor(private val sdk: Sdk) {
fun getAttendanceSummary(semester: Semester, subjectId: Int): Single<List<AttendanceSummary>> { fun getAttendanceSummary(student: Student, semester: Semester, subjectId: Int): Single<List<AttendanceSummary>> {
return sdk.switchDiary(semester.diaryId, semester.schoolYear).getAttendanceSummary(subjectId) return sdk.init(student).switchDiary(semester.diaryId, semester.schoolYear)
.getAttendanceSummary(subjectId)
.map { attendance -> .map { attendance ->
attendance.map { attendance.map {
AttendanceSummary( AttendanceSummary(

View File

@ -4,6 +4,7 @@ import com.github.pwittchen.reactivenetwork.library.rx2.ReactiveNetwork
import com.github.pwittchen.reactivenetwork.library.rx2.internet.observing.InternetObservingSettings import com.github.pwittchen.reactivenetwork.library.rx2.internet.observing.InternetObservingSettings
import io.github.wulkanowy.data.db.entities.AttendanceSummary import io.github.wulkanowy.data.db.entities.AttendanceSummary
import io.github.wulkanowy.data.db.entities.Semester import io.github.wulkanowy.data.db.entities.Semester
import io.github.wulkanowy.data.db.entities.Student
import io.github.wulkanowy.utils.uniqueSubtract import io.github.wulkanowy.utils.uniqueSubtract
import io.reactivex.Single import io.reactivex.Single
import java.net.UnknownHostException import java.net.UnknownHostException
@ -17,11 +18,11 @@ class AttendanceSummaryRepository @Inject constructor(
private val remote: AttendanceSummaryRemote private val remote: AttendanceSummaryRemote
) { ) {
fun getAttendanceSummary(semester: Semester, subjectId: Int, forceRefresh: Boolean = false): Single<List<AttendanceSummary>> { fun getAttendanceSummary(student: Student, semester: Semester, subjectId: Int, forceRefresh: Boolean = false): Single<List<AttendanceSummary>> {
return local.getAttendanceSummary(semester, subjectId).filter { !forceRefresh } return local.getAttendanceSummary(semester, subjectId).filter { !forceRefresh }
.switchIfEmpty(ReactiveNetwork.checkInternetConnectivity(settings) .switchIfEmpty(ReactiveNetwork.checkInternetConnectivity(settings)
.flatMap { .flatMap {
if (it) remote.getAttendanceSummary(semester, subjectId) if (it) remote.getAttendanceSummary(student, semester, subjectId)
else Single.error(UnknownHostException()) else Single.error(UnknownHostException())
}.flatMap { new -> }.flatMap { new ->
local.getAttendanceSummary(semester, subjectId).toSingle(emptyList()) local.getAttendanceSummary(semester, subjectId).toSingle(emptyList())

View File

@ -2,7 +2,9 @@ package io.github.wulkanowy.data.repositories.completedlessons
import io.github.wulkanowy.data.db.entities.CompletedLesson import io.github.wulkanowy.data.db.entities.CompletedLesson
import io.github.wulkanowy.data.db.entities.Semester import io.github.wulkanowy.data.db.entities.Semester
import io.github.wulkanowy.data.db.entities.Student
import io.github.wulkanowy.sdk.Sdk import io.github.wulkanowy.sdk.Sdk
import io.github.wulkanowy.utils.init
import io.reactivex.Single import io.reactivex.Single
import org.threeten.bp.LocalDate import org.threeten.bp.LocalDate
import javax.inject.Inject import javax.inject.Inject
@ -11,8 +13,9 @@ import javax.inject.Singleton
@Singleton @Singleton
class CompletedLessonsRemote @Inject constructor(private val sdk: Sdk) { class CompletedLessonsRemote @Inject constructor(private val sdk: Sdk) {
fun getCompletedLessons(semester: Semester, startDate: LocalDate, endDate: LocalDate): Single<List<CompletedLesson>> { fun getCompletedLessons(student: Student, semester: Semester, startDate: LocalDate, endDate: LocalDate): Single<List<CompletedLesson>> {
return sdk.switchDiary(semester.diaryId, semester.schoolYear).getCompletedLessons(startDate, endDate) return sdk.init(student).switchDiary(semester.diaryId, semester.schoolYear)
.getCompletedLessons(startDate, endDate)
.map { lessons -> .map { lessons ->
lessons.map { lessons.map {
it.absence it.absence

View File

@ -4,6 +4,7 @@ import com.github.pwittchen.reactivenetwork.library.rx2.ReactiveNetwork
import com.github.pwittchen.reactivenetwork.library.rx2.internet.observing.InternetObservingSettings import com.github.pwittchen.reactivenetwork.library.rx2.internet.observing.InternetObservingSettings
import io.github.wulkanowy.data.db.entities.CompletedLesson import io.github.wulkanowy.data.db.entities.CompletedLesson
import io.github.wulkanowy.data.db.entities.Semester import io.github.wulkanowy.data.db.entities.Semester
import io.github.wulkanowy.data.db.entities.Student
import io.github.wulkanowy.utils.friday import io.github.wulkanowy.utils.friday
import io.github.wulkanowy.utils.monday import io.github.wulkanowy.utils.monday
import io.github.wulkanowy.utils.uniqueSubtract import io.github.wulkanowy.utils.uniqueSubtract
@ -20,25 +21,22 @@ class CompletedLessonsRepository @Inject constructor(
private val remote: CompletedLessonsRemote private val remote: CompletedLessonsRemote
) { ) {
fun getCompletedLessons(semester: Semester, startDate: LocalDate, endDate: LocalDate, forceRefresh: Boolean = false): Single<List<CompletedLesson>> { fun getCompletedLessons(student: Student, semester: Semester, start: LocalDate, end: LocalDate, forceRefresh: Boolean = false): Single<List<CompletedLesson>> {
return Single.fromCallable { startDate.monday to endDate.friday } return local.getCompletedLessons(semester, start.monday, end.friday).filter { !forceRefresh }
.flatMap { dates ->
local.getCompletedLessons(semester, dates.first, dates.second).filter { !forceRefresh }
.switchIfEmpty(ReactiveNetwork.checkInternetConnectivity(settings) .switchIfEmpty(ReactiveNetwork.checkInternetConnectivity(settings)
.flatMap { .flatMap {
if (it) remote.getCompletedLessons(semester, dates.first, dates.second) if (it) remote.getCompletedLessons(student, semester, start.monday, end.friday)
else Single.error(UnknownHostException()) else Single.error(UnknownHostException())
}.flatMap { new -> }.flatMap { new ->
local.getCompletedLessons(semester, dates.first, dates.second) local.getCompletedLessons(semester, start.monday, end.friday)
.toSingle(emptyList()) .toSingle(emptyList())
.doOnSuccess { old -> .doOnSuccess { old ->
local.deleteCompleteLessons(old.uniqueSubtract(new)) local.deleteCompleteLessons(old.uniqueSubtract(new))
local.saveCompletedLessons(new.uniqueSubtract(old)) local.saveCompletedLessons(new.uniqueSubtract(old))
} }
}.flatMap { }.flatMap {
local.getCompletedLessons(semester, dates.first, dates.second) local.getCompletedLessons(semester, start.monday, end.friday)
.toSingle(emptyList()) .toSingle(emptyList())
}).map { list -> list.filter { it.date in startDate..endDate } } }).map { list -> list.filter { it.date in start..end } }
}
} }
} }

View File

@ -2,7 +2,9 @@ package io.github.wulkanowy.data.repositories.exam
import io.github.wulkanowy.data.db.entities.Exam import io.github.wulkanowy.data.db.entities.Exam
import io.github.wulkanowy.data.db.entities.Semester import io.github.wulkanowy.data.db.entities.Semester
import io.github.wulkanowy.data.db.entities.Student
import io.github.wulkanowy.sdk.Sdk import io.github.wulkanowy.sdk.Sdk
import io.github.wulkanowy.utils.init
import io.reactivex.Single import io.reactivex.Single
import org.threeten.bp.LocalDate import org.threeten.bp.LocalDate
import javax.inject.Inject import javax.inject.Inject
@ -11,8 +13,9 @@ import javax.inject.Singleton
@Singleton @Singleton
class ExamRemote @Inject constructor(private val sdk: Sdk) { class ExamRemote @Inject constructor(private val sdk: Sdk) {
fun getExams(semester: Semester, startDate: LocalDate, endDate: LocalDate): Single<List<Exam>> { fun getExams(student: Student, semester: Semester, startDate: LocalDate, endDate: LocalDate): Single<List<Exam>> {
return sdk.switchDiary(semester.diaryId, semester.schoolYear).getExams(startDate, endDate, semester.semesterId) return sdk.init(student).switchDiary(semester.diaryId, semester.schoolYear)
.getExams(startDate, endDate, semester.semesterId)
.map { exams -> .map { exams ->
exams.map { exams.map {
Exam( Exam(

View File

@ -4,6 +4,7 @@ import com.github.pwittchen.reactivenetwork.library.rx2.ReactiveNetwork
import com.github.pwittchen.reactivenetwork.library.rx2.internet.observing.InternetObservingSettings import com.github.pwittchen.reactivenetwork.library.rx2.internet.observing.InternetObservingSettings
import io.github.wulkanowy.data.db.entities.Exam import io.github.wulkanowy.data.db.entities.Exam
import io.github.wulkanowy.data.db.entities.Semester import io.github.wulkanowy.data.db.entities.Semester
import io.github.wulkanowy.data.db.entities.Student
import io.github.wulkanowy.utils.friday import io.github.wulkanowy.utils.friday
import io.github.wulkanowy.utils.monday import io.github.wulkanowy.utils.monday
import io.github.wulkanowy.utils.uniqueSubtract import io.github.wulkanowy.utils.uniqueSubtract
@ -20,25 +21,22 @@ class ExamRepository @Inject constructor(
private val remote: ExamRemote private val remote: ExamRemote
) { ) {
fun getExams(semester: Semester, startDate: LocalDate, endDate: LocalDate, forceRefresh: Boolean = false): Single<List<Exam>> { fun getExams(student: Student, semester: Semester, start: LocalDate, end: LocalDate, forceRefresh: Boolean = false): Single<List<Exam>> {
return Single.fromCallable { startDate.monday to endDate.friday } return local.getExams(semester, start.monday, end.friday).filter { !forceRefresh }
.flatMap { dates ->
local.getExams(semester, dates.first, dates.second).filter { !forceRefresh }
.switchIfEmpty(ReactiveNetwork.checkInternetConnectivity(settings) .switchIfEmpty(ReactiveNetwork.checkInternetConnectivity(settings)
.flatMap { .flatMap {
if (it) remote.getExams(semester, dates.first, dates.second) if (it) remote.getExams(student, semester, start.monday, end.friday)
else Single.error(UnknownHostException()) else Single.error(UnknownHostException())
}.flatMap { new -> }.flatMap { new ->
local.getExams(semester, dates.first, dates.second) local.getExams(semester, start.monday, end.friday)
.toSingle(emptyList()) .toSingle(emptyList())
.doOnSuccess { old -> .doOnSuccess { old ->
local.deleteExams(old.uniqueSubtract(new)) local.deleteExams(old.uniqueSubtract(new))
local.saveExams(new.uniqueSubtract(old)) local.saveExams(new.uniqueSubtract(old))
} }
}.flatMap { }.flatMap {
local.getExams(semester, dates.first, dates.second) local.getExams(semester, start.monday, end.friday)
.toSingle(emptyList()) .toSingle(emptyList())
}).map { list -> list.filter { it.date in startDate..endDate } } }).map { list -> list.filter { it.date in start..end } }
}
} }
} }

View File

@ -2,7 +2,9 @@ package io.github.wulkanowy.data.repositories.grade
import io.github.wulkanowy.data.db.entities.Grade import io.github.wulkanowy.data.db.entities.Grade
import io.github.wulkanowy.data.db.entities.Semester import io.github.wulkanowy.data.db.entities.Semester
import io.github.wulkanowy.data.db.entities.Student
import io.github.wulkanowy.sdk.Sdk import io.github.wulkanowy.sdk.Sdk
import io.github.wulkanowy.utils.init
import io.reactivex.Single import io.reactivex.Single
import javax.inject.Inject import javax.inject.Inject
import javax.inject.Singleton import javax.inject.Singleton
@ -10,8 +12,9 @@ import javax.inject.Singleton
@Singleton @Singleton
class GradeRemote @Inject constructor(private val sdk: Sdk) { class GradeRemote @Inject constructor(private val sdk: Sdk) {
fun getGrades(semester: Semester): Single<List<Grade>> { fun getGrades(student: Student, semester: Semester): Single<List<Grade>> {
return sdk.switchDiary(semester.diaryId, semester.schoolYear).getGrades(semester.semesterId) return sdk.init(student).switchDiary(semester.diaryId, semester.schoolYear)
.getGrades(semester.semesterId)
.map { grades -> .map { grades ->
grades.map { grades.map {
Grade( Grade(

View File

@ -23,7 +23,7 @@ class GradeRepository @Inject constructor(
return local.getGrades(semester).filter { !forceRefresh } return local.getGrades(semester).filter { !forceRefresh }
.switchIfEmpty(ReactiveNetwork.checkInternetConnectivity(settings) .switchIfEmpty(ReactiveNetwork.checkInternetConnectivity(settings)
.flatMap { .flatMap {
if (it) remote.getGrades(semester) if (it) remote.getGrades(student, semester)
else Single.error(UnknownHostException()) else Single.error(UnknownHostException())
}.flatMap { new -> }.flatMap { new ->
local.getGrades(semester).toSingle(emptyList()) local.getGrades(semester).toSingle(emptyList())

View File

@ -2,7 +2,9 @@ package io.github.wulkanowy.data.repositories.gradessummary
import io.github.wulkanowy.data.db.entities.GradeSummary import io.github.wulkanowy.data.db.entities.GradeSummary
import io.github.wulkanowy.data.db.entities.Semester import io.github.wulkanowy.data.db.entities.Semester
import io.github.wulkanowy.data.db.entities.Student
import io.github.wulkanowy.sdk.Sdk import io.github.wulkanowy.sdk.Sdk
import io.github.wulkanowy.utils.init
import io.reactivex.Single import io.reactivex.Single
import javax.inject.Inject import javax.inject.Inject
import javax.inject.Singleton import javax.inject.Singleton
@ -10,8 +12,9 @@ import javax.inject.Singleton
@Singleton @Singleton
class GradeSummaryRemote @Inject constructor(private val sdk: Sdk) { class GradeSummaryRemote @Inject constructor(private val sdk: Sdk) {
fun getGradeSummary(semester: Semester): Single<List<GradeSummary>> { fun getGradeSummary(student: Student, semester: Semester): Single<List<GradeSummary>> {
return sdk.switchDiary(semester.diaryId, semester.schoolYear).getGradesSummary(semester.semesterId) return sdk.init(student).switchDiary(semester.diaryId, semester.schoolYear)
.getGradesSummary(semester.semesterId)
.map { gradesSummary -> .map { gradesSummary ->
gradesSummary.map { gradesSummary.map {
GradeSummary( GradeSummary(

View File

@ -4,6 +4,7 @@ import com.github.pwittchen.reactivenetwork.library.rx2.ReactiveNetwork
import com.github.pwittchen.reactivenetwork.library.rx2.internet.observing.InternetObservingSettings import com.github.pwittchen.reactivenetwork.library.rx2.internet.observing.InternetObservingSettings
import io.github.wulkanowy.data.db.entities.GradeSummary import io.github.wulkanowy.data.db.entities.GradeSummary
import io.github.wulkanowy.data.db.entities.Semester import io.github.wulkanowy.data.db.entities.Semester
import io.github.wulkanowy.data.db.entities.Student
import io.github.wulkanowy.utils.uniqueSubtract import io.github.wulkanowy.utils.uniqueSubtract
import io.reactivex.Single import io.reactivex.Single
import java.net.UnknownHostException import java.net.UnknownHostException
@ -17,11 +18,11 @@ class GradeSummaryRepository @Inject constructor(
private val remote: GradeSummaryRemote private val remote: GradeSummaryRemote
) { ) {
fun getGradesSummary(semester: Semester, forceRefresh: Boolean = false): Single<List<GradeSummary>> { fun getGradesSummary(student: Student, semester: Semester, forceRefresh: Boolean = false): Single<List<GradeSummary>> {
return local.getGradesSummary(semester).filter { !forceRefresh } return local.getGradesSummary(semester).filter { !forceRefresh }
.switchIfEmpty(ReactiveNetwork.checkInternetConnectivity(settings) .switchIfEmpty(ReactiveNetwork.checkInternetConnectivity(settings)
.flatMap { .flatMap {
if (it) remote.getGradeSummary(semester) if (it) remote.getGradeSummary(student, semester)
else Single.error(UnknownHostException()) else Single.error(UnknownHostException())
}.flatMap { new -> }.flatMap { new ->
local.getGradesSummary(semester).toSingle(emptyList()) local.getGradesSummary(semester).toSingle(emptyList())

View File

@ -5,7 +5,6 @@ import io.github.wulkanowy.data.db.dao.GradeStatisticsDao
import io.github.wulkanowy.data.db.entities.GradePointsStatistics import io.github.wulkanowy.data.db.entities.GradePointsStatistics
import io.github.wulkanowy.data.db.entities.GradeStatistics import io.github.wulkanowy.data.db.entities.GradeStatistics
import io.github.wulkanowy.data.db.entities.Semester import io.github.wulkanowy.data.db.entities.Semester
import io.github.wulkanowy.utils.roundToDecimalPlaces
import io.reactivex.Maybe import io.reactivex.Maybe
import javax.inject.Inject import javax.inject.Inject
import javax.inject.Singleton import javax.inject.Singleton
@ -30,23 +29,17 @@ class GradeStatisticsLocal @Inject constructor(
list.groupBy { it.grade }.map { list.groupBy { it.grade }.map {
GradeStatistics(semester.studentId, semester.semesterId, subjectName, it.key, GradeStatistics(semester.studentId, semester.semesterId, subjectName, it.key,
it.value.fold(0) { acc, e -> acc + e.amount }, false) it.value.fold(0) { acc, e -> acc + e.amount }, false)
} } + list
} }
else -> gradeStatisticsDb.loadSubject(semester.semesterId, semester.studentId, subjectName, isSemester) else -> gradeStatisticsDb.loadSubject(semester.semesterId, semester.studentId, subjectName, isSemester)
}.filter { it.isNotEmpty() } }.filter { it.isNotEmpty() }
} }
fun getGradesPointsStatistics(semester: Semester, subjectName: String): Maybe<GradePointsStatistics> { fun getGradesPointsStatistics(semester: Semester, subjectName: String): Maybe<List<GradePointsStatistics>> {
return when (subjectName) { return when (subjectName) {
"Wszystkie" -> gradePointsStatisticsDb.loadAll(semester.semesterId, semester.studentId).flatMap { list -> "Wszystkie" -> gradePointsStatisticsDb.loadAll(semester.semesterId, semester.studentId)
if (list.isEmpty()) return@flatMap Maybe.empty<GradePointsStatistics>()
Maybe.just(GradePointsStatistics(semester.studentId, semester.semesterId, subjectName,
(list.fold(.0) { acc, e -> acc + e.others } / list.size).roundToDecimalPlaces(2),
(list.fold(.0) { acc, e -> acc + e.student } / list.size).roundToDecimalPlaces(2)
))
}
else -> gradePointsStatisticsDb.loadSubject(semester.semesterId, semester.studentId, subjectName) else -> gradePointsStatisticsDb.loadSubject(semester.semesterId, semester.studentId, subjectName)
} }.filter { it.isNotEmpty() }
} }
fun saveGradesStatistics(gradesStatistics: List<GradeStatistics>) { fun saveGradesStatistics(gradesStatistics: List<GradeStatistics>) {

View File

@ -3,7 +3,9 @@ package io.github.wulkanowy.data.repositories.gradestatistics
import io.github.wulkanowy.data.db.entities.GradePointsStatistics import io.github.wulkanowy.data.db.entities.GradePointsStatistics
import io.github.wulkanowy.data.db.entities.GradeStatistics import io.github.wulkanowy.data.db.entities.GradeStatistics
import io.github.wulkanowy.data.db.entities.Semester import io.github.wulkanowy.data.db.entities.Semester
import io.github.wulkanowy.data.db.entities.Student
import io.github.wulkanowy.sdk.Sdk import io.github.wulkanowy.sdk.Sdk
import io.github.wulkanowy.utils.init
import io.reactivex.Single import io.reactivex.Single
import javax.inject.Inject import javax.inject.Inject
import javax.inject.Singleton import javax.inject.Singleton
@ -11,8 +13,8 @@ import javax.inject.Singleton
@Singleton @Singleton
class GradeStatisticsRemote @Inject constructor(private val sdk: Sdk) { class GradeStatisticsRemote @Inject constructor(private val sdk: Sdk) {
fun getGradeStatistics(semester: Semester, isSemester: Boolean): Single<List<GradeStatistics>> { fun getGradeStatistics(student: Student, semester: Semester, isSemester: Boolean): Single<List<GradeStatistics>> {
return sdk.switchDiary(semester.diaryId, semester.schoolYear).let { return sdk.init(student).switchDiary(semester.diaryId, semester.schoolYear).let {
if (isSemester) it.getGradesAnnualStatistics(semester.semesterId) if (isSemester) it.getGradesAnnualStatistics(semester.semesterId)
else it.getGradesPartialStatistics(semester.semesterId) else it.getGradesPartialStatistics(semester.semesterId)
}.map { gradeStatistics -> }.map { gradeStatistics ->
@ -29,8 +31,9 @@ class GradeStatisticsRemote @Inject constructor(private val sdk: Sdk) {
} }
} }
fun getGradePointsStatistics(semester: Semester): Single<List<GradePointsStatistics>> { fun getGradePointsStatistics(student: Student, semester: Semester): Single<List<GradePointsStatistics>> {
return sdk.switchDiary(semester.diaryId, semester.schoolYear).getGradesPointsStatistics(semester.semesterId) return sdk.init(student).switchDiary(semester.diaryId, semester.schoolYear)
.getGradesPointsStatistics(semester.semesterId)
.map { gradePointsStatistics -> .map { gradePointsStatistics ->
gradePointsStatistics.map { gradePointsStatistics.map {
GradePointsStatistics( GradePointsStatistics(

View File

@ -5,8 +5,10 @@ import com.github.pwittchen.reactivenetwork.library.rx2.internet.observing.Inter
import io.github.wulkanowy.data.db.entities.GradePointsStatistics import io.github.wulkanowy.data.db.entities.GradePointsStatistics
import io.github.wulkanowy.data.db.entities.GradeStatistics import io.github.wulkanowy.data.db.entities.GradeStatistics
import io.github.wulkanowy.data.db.entities.Semester import io.github.wulkanowy.data.db.entities.Semester
import io.github.wulkanowy.data.db.entities.Student
import io.github.wulkanowy.data.pojos.GradeStatisticsItem
import io.github.wulkanowy.ui.modules.grade.statistics.ViewType
import io.github.wulkanowy.utils.uniqueSubtract import io.github.wulkanowy.utils.uniqueSubtract
import io.reactivex.Maybe
import io.reactivex.Single import io.reactivex.Single
import java.net.UnknownHostException import java.net.UnknownHostException
import javax.inject.Inject import javax.inject.Inject
@ -19,11 +21,11 @@ class GradeStatisticsRepository @Inject constructor(
private val remote: GradeStatisticsRemote private val remote: GradeStatisticsRemote
) { ) {
fun getGradesStatistics(semester: Semester, subjectName: String, isSemester: Boolean, forceRefresh: Boolean = false): Single<List<GradeStatistics>> { fun getGradesStatistics(student: Student, semester: Semester, subjectName: String, isSemester: Boolean, forceRefresh: Boolean = false): Single<List<GradeStatisticsItem>> {
return local.getGradesStatistics(semester, isSemester, subjectName).filter { !forceRefresh } return local.getGradesStatistics(semester, isSemester, subjectName).map { it.mapToStatisticItems() }.filter { !forceRefresh }
.switchIfEmpty(ReactiveNetwork.checkInternetConnectivity(settings) .switchIfEmpty(ReactiveNetwork.checkInternetConnectivity(settings)
.flatMap { .flatMap {
if (it) remote.getGradeStatistics(semester, isSemester) if (it) remote.getGradeStatistics(student, semester, isSemester)
else Single.error(UnknownHostException()) else Single.error(UnknownHostException())
}.flatMap { new -> }.flatMap { new ->
local.getGradesStatistics(semester, isSemester).toSingle(emptyList()) local.getGradesStatistics(semester, isSemester).toSingle(emptyList())
@ -31,21 +33,43 @@ class GradeStatisticsRepository @Inject constructor(
local.deleteGradesStatistics(old.uniqueSubtract(new)) local.deleteGradesStatistics(old.uniqueSubtract(new))
local.saveGradesStatistics(new.uniqueSubtract(old)) local.saveGradesStatistics(new.uniqueSubtract(old))
} }
}.flatMap { local.getGradesStatistics(semester, isSemester, subjectName).toSingle(emptyList()) }) }.flatMap { local.getGradesStatistics(semester, isSemester, subjectName).map { it.mapToStatisticItems() }.toSingle(emptyList()) })
} }
fun getGradesPointsStatistics(semester: Semester, subjectName: String, forceRefresh: Boolean): Maybe<GradePointsStatistics> { fun getGradesPointsStatistics(student: Student, semester: Semester, subjectName: String, forceRefresh: Boolean): Single<List<GradeStatisticsItem>> {
return local.getGradesPointsStatistics(semester, subjectName).filter { !forceRefresh } return local.getGradesPointsStatistics(semester, subjectName).map { it.mapToStatisticsItem() }.filter { !forceRefresh }
.switchIfEmpty(ReactiveNetwork.checkInternetConnectivity(settings) .switchIfEmpty(ReactiveNetwork.checkInternetConnectivity(settings)
.flatMapMaybe { .flatMap {
if (it) remote.getGradePointsStatistics(semester).toMaybe() if (it) remote.getGradePointsStatistics(student, semester)
else Maybe.error(UnknownHostException()) else Single.error(UnknownHostException())
}.flatMap { new -> }.flatMap { new ->
local.getGradesPointsStatistics(semester).defaultIfEmpty(emptyList()) local.getGradesPointsStatistics(semester).toSingle(emptyList())
.doOnSuccess { old -> .doOnSuccess { old ->
local.deleteGradesPointsStatistics(old.uniqueSubtract(new)) local.deleteGradesPointsStatistics(old.uniqueSubtract(new))
local.saveGradesPointsStatistics(new.uniqueSubtract(old)) local.saveGradesPointsStatistics(new.uniqueSubtract(old))
} }
}.flatMap { local.getGradesPointsStatistics(semester, subjectName) }) }.flatMap { local.getGradesPointsStatistics(semester, subjectName).map { it.mapToStatisticsItem() }.toSingle(emptyList()) })
}
private fun List<GradeStatistics>.mapToStatisticItems(): List<GradeStatisticsItem> {
return groupBy { it.subject }.map {
GradeStatisticsItem(
type = ViewType.PARTIAL,
partial = it.value
.sortedByDescending { item -> item.grade }
.filter { item -> item.amount != 0 },
points = null
)
}
}
private fun List<GradePointsStatistics>.mapToStatisticsItem(): List<GradeStatisticsItem> {
return map {
GradeStatisticsItem(
type = ViewType.POINTS,
partial = emptyList(),
points = it
)
}
} }
} }

View File

@ -19,6 +19,10 @@ class HomeworkLocal @Inject constructor(private val homeworkDb: HomeworkDao) {
homeworkDb.deleteAll(homework) homeworkDb.deleteAll(homework)
} }
fun updateHomework(homework: List<Homework>) {
homeworkDb.updateAll(homework)
}
fun getHomework(semester: Semester, startDate: LocalDate, endDate: LocalDate): Maybe<List<Homework>> { fun getHomework(semester: Semester, startDate: LocalDate, endDate: LocalDate): Maybe<List<Homework>> {
return homeworkDb.loadAll(semester.semesterId, semester.studentId, startDate, endDate) return homeworkDb.loadAll(semester.semesterId, semester.studentId, startDate, endDate)
.filter { it.isNotEmpty() } .filter { it.isNotEmpty() }

View File

@ -2,7 +2,9 @@ package io.github.wulkanowy.data.repositories.homework
import io.github.wulkanowy.data.db.entities.Homework import io.github.wulkanowy.data.db.entities.Homework
import io.github.wulkanowy.data.db.entities.Semester import io.github.wulkanowy.data.db.entities.Semester
import io.github.wulkanowy.data.db.entities.Student
import io.github.wulkanowy.sdk.Sdk import io.github.wulkanowy.sdk.Sdk
import io.github.wulkanowy.utils.init
import io.reactivex.Single import io.reactivex.Single
import org.threeten.bp.LocalDate import org.threeten.bp.LocalDate
import javax.inject.Inject import javax.inject.Inject
@ -11,8 +13,9 @@ import javax.inject.Singleton
@Singleton @Singleton
class HomeworkRemote @Inject constructor(private val sdk: Sdk) { class HomeworkRemote @Inject constructor(private val sdk: Sdk) {
fun getHomework(semester: Semester, startDate: LocalDate, endDate: LocalDate): Single<List<Homework>> { fun getHomework(student: Student, semester: Semester, startDate: LocalDate, endDate: LocalDate): Single<List<Homework>> {
return sdk.switchDiary(semester.diaryId, semester.schoolYear).getHomework(startDate, endDate) return sdk.init(student).switchDiary(semester.diaryId, semester.schoolYear)
.getHomework(startDate, endDate)
.map { homework -> .map { homework ->
homework.map { homework.map {
Homework( Homework(
@ -23,7 +26,8 @@ class HomeworkRemote @Inject constructor(private val sdk: Sdk) {
subject = it.subject, subject = it.subject,
content = it.content, content = it.content,
teacher = it.teacher, teacher = it.teacher,
teacherSymbol = it.teacherSymbol teacherSymbol = it.teacherSymbol,
attachments = it.attachments.map { attachment -> attachment.url to attachment.name }
) )
} }
} }

View File

@ -4,9 +4,11 @@ import com.github.pwittchen.reactivenetwork.library.rx2.ReactiveNetwork
import com.github.pwittchen.reactivenetwork.library.rx2.internet.observing.InternetObservingSettings import com.github.pwittchen.reactivenetwork.library.rx2.internet.observing.InternetObservingSettings
import io.github.wulkanowy.data.db.entities.Homework import io.github.wulkanowy.data.db.entities.Homework
import io.github.wulkanowy.data.db.entities.Semester import io.github.wulkanowy.data.db.entities.Semester
import io.github.wulkanowy.data.db.entities.Student
import io.github.wulkanowy.utils.friday import io.github.wulkanowy.utils.friday
import io.github.wulkanowy.utils.monday import io.github.wulkanowy.utils.monday
import io.github.wulkanowy.utils.uniqueSubtract import io.github.wulkanowy.utils.uniqueSubtract
import io.reactivex.Completable
import io.reactivex.Single import io.reactivex.Single
import org.threeten.bp.LocalDate import org.threeten.bp.LocalDate
import java.net.UnknownHostException import java.net.UnknownHostException
@ -20,12 +22,12 @@ class HomeworkRepository @Inject constructor(
private val remote: HomeworkRemote private val remote: HomeworkRemote
) { ) {
fun getHomework(semester: Semester, start: LocalDate, end: LocalDate, forceRefresh: Boolean = false): Single<List<Homework>> { fun getHomework(student: Student, semester: Semester, start: LocalDate, end: LocalDate, forceRefresh: Boolean = false): Single<List<Homework>> {
return Single.fromCallable { start.monday to end.friday }.flatMap { (monday, friday) -> return Single.fromCallable { start.monday to end.friday }.flatMap { (monday, friday) ->
local.getHomework(semester, monday, friday).filter { !forceRefresh } local.getHomework(semester, monday, friday).filter { !forceRefresh }
.switchIfEmpty(ReactiveNetwork.checkInternetConnectivity(settings) .switchIfEmpty(ReactiveNetwork.checkInternetConnectivity(settings)
.flatMap { .flatMap {
if (it) remote.getHomework(semester, monday, friday) if (it) remote.getHomework(student, semester, monday, friday)
else Single.error(UnknownHostException()) else Single.error(UnknownHostException())
}.flatMap { new -> }.flatMap { new ->
local.getHomework(semester, monday, friday).toSingle(emptyList()) local.getHomework(semester, monday, friday).toSingle(emptyList())
@ -36,4 +38,12 @@ class HomeworkRepository @Inject constructor(
}.flatMap { local.getHomework(semester, monday, friday).toSingle(emptyList()) }) }.flatMap { local.getHomework(semester, monday, friday).toSingle(emptyList()) })
} }
} }
fun toggleDone(homework: Homework): Completable {
return Completable.fromCallable {
local.updateHomework(listOf(homework.apply {
isDone = !isDone
}))
}
}
} }

View File

@ -0,0 +1,39 @@
package io.github.wulkanowy.data.repositories.logger
import android.content.Context
import io.reactivex.Single
import java.io.File
import java.io.FileNotFoundException
import javax.inject.Inject
class LoggerRepository @Inject constructor(private val context: Context) {
fun getLastLogLines(): Single<List<String>> {
return getLastModified()
.map { it.readText() }
.map { it.split("\n") }
}
fun getLogFiles(): Single<List<File>> {
return Single.fromCallable {
File(context.filesDir.absolutePath).listFiles(File::isFile)?.filter {
it.name.endsWith(".log")
}
}
}
private fun getLastModified(): Single<File> {
return Single.fromCallable {
var lastModifiedTime = Long.MIN_VALUE
var chosenFile: File? = null
File(context.filesDir.absolutePath).listFiles(File::isFile)?.forEach { file ->
if (file.lastModified() > lastModifiedTime) {
lastModifiedTime = file.lastModified()
chosenFile = file
}
}
if (chosenFile == null) throw FileNotFoundException("Log file not found")
chosenFile
}
}
}

View File

@ -2,7 +2,7 @@ package io.github.wulkanowy.data.repositories.luckynumber
import io.github.wulkanowy.data.db.dao.LuckyNumberDao import io.github.wulkanowy.data.db.dao.LuckyNumberDao
import io.github.wulkanowy.data.db.entities.LuckyNumber import io.github.wulkanowy.data.db.entities.LuckyNumber
import io.github.wulkanowy.data.db.entities.Semester import io.github.wulkanowy.data.db.entities.Student
import io.reactivex.Maybe import io.reactivex.Maybe
import org.threeten.bp.LocalDate import org.threeten.bp.LocalDate
import javax.inject.Inject import javax.inject.Inject
@ -23,7 +23,7 @@ class LuckyNumberLocal @Inject constructor(private val luckyNumberDb: LuckyNumbe
luckyNumberDb.deleteAll(listOf(luckyNumber)) luckyNumberDb.deleteAll(listOf(luckyNumber))
} }
fun getLuckyNumber(semester: Semester, date: LocalDate): Maybe<LuckyNumber> { fun getLuckyNumber(student: Student, date: LocalDate): Maybe<LuckyNumber> {
return luckyNumberDb.load(semester.studentId, date) return luckyNumberDb.load(student.studentId, date)
} }
} }

View File

@ -1,8 +1,9 @@
package io.github.wulkanowy.data.repositories.luckynumber package io.github.wulkanowy.data.repositories.luckynumber
import io.github.wulkanowy.data.db.entities.LuckyNumber import io.github.wulkanowy.data.db.entities.LuckyNumber
import io.github.wulkanowy.data.db.entities.Semester import io.github.wulkanowy.data.db.entities.Student
import io.github.wulkanowy.sdk.Sdk import io.github.wulkanowy.sdk.Sdk
import io.github.wulkanowy.utils.init
import io.reactivex.Maybe import io.reactivex.Maybe
import org.threeten.bp.LocalDate import org.threeten.bp.LocalDate
import javax.inject.Inject import javax.inject.Inject
@ -11,11 +12,10 @@ import javax.inject.Singleton
@Singleton @Singleton
class LuckyNumberRemote @Inject constructor(private val sdk: Sdk) { class LuckyNumberRemote @Inject constructor(private val sdk: Sdk) {
fun getLuckyNumber(semester: Semester): Maybe<LuckyNumber> { fun getLuckyNumber(student: Student): Maybe<LuckyNumber> {
return sdk.getLuckyNumber() return sdk.init(student).getLuckyNumber(student.schoolShortName).map {
.map {
LuckyNumber( LuckyNumber(
studentId = semester.studentId, studentId = student.studentId,
date = LocalDate.now(), date = LocalDate.now(),
luckyNumber = it luckyNumber = it
) )

View File

@ -3,7 +3,7 @@ package io.github.wulkanowy.data.repositories.luckynumber
import com.github.pwittchen.reactivenetwork.library.rx2.ReactiveNetwork import com.github.pwittchen.reactivenetwork.library.rx2.ReactiveNetwork
import com.github.pwittchen.reactivenetwork.library.rx2.internet.observing.InternetObservingSettings import com.github.pwittchen.reactivenetwork.library.rx2.internet.observing.InternetObservingSettings
import io.github.wulkanowy.data.db.entities.LuckyNumber import io.github.wulkanowy.data.db.entities.LuckyNumber
import io.github.wulkanowy.data.db.entities.Semester import io.github.wulkanowy.data.db.entities.Student
import io.reactivex.Completable import io.reactivex.Completable
import io.reactivex.Maybe import io.reactivex.Maybe
import org.threeten.bp.LocalDate import org.threeten.bp.LocalDate
@ -18,14 +18,14 @@ class LuckyNumberRepository @Inject constructor(
private val remote: LuckyNumberRemote private val remote: LuckyNumberRemote
) { ) {
fun getLuckyNumber(semester: Semester, forceRefresh: Boolean = false, notify: Boolean = false): Maybe<LuckyNumber> { fun getLuckyNumber(student: Student, forceRefresh: Boolean = false, notify: Boolean = false): Maybe<LuckyNumber> {
return local.getLuckyNumber(semester, LocalDate.now()).filter { !forceRefresh } return local.getLuckyNumber(student, LocalDate.now()).filter { !forceRefresh }
.switchIfEmpty(ReactiveNetwork.checkInternetConnectivity(settings) .switchIfEmpty(ReactiveNetwork.checkInternetConnectivity(settings)
.flatMapMaybe { .flatMapMaybe {
if (it) remote.getLuckyNumber(semester) if (it) remote.getLuckyNumber(student)
else Maybe.error(UnknownHostException()) else Maybe.error(UnknownHostException())
}.flatMap { new -> }.flatMap { new ->
local.getLuckyNumber(semester, LocalDate.now()) local.getLuckyNumber(student, LocalDate.now())
.doOnSuccess { old -> .doOnSuccess { old ->
if (new != old) { if (new != old) {
local.deleteLuckyNumber(old) local.deleteLuckyNumber(old)
@ -39,13 +39,13 @@ class LuckyNumberRepository @Inject constructor(
if (notify) isNotified = false if (notify) isNotified = false
}) })
} }
}.flatMap({ local.getLuckyNumber(semester, LocalDate.now()) }, { Maybe.error(it) }, }.flatMap({ local.getLuckyNumber(student, LocalDate.now()) }, { Maybe.error(it) },
{ local.getLuckyNumber(semester, LocalDate.now()) }) { local.getLuckyNumber(student, LocalDate.now()) })
) )
} }
fun getNotNotifiedLuckyNumber(semester: Semester): Maybe<LuckyNumber> { fun getNotNotifiedLuckyNumber(student: Student): Maybe<LuckyNumber> {
return local.getLuckyNumber(semester, LocalDate.now()).filter { !it.isNotified } return local.getLuckyNumber(student, LocalDate.now()).filter { !it.isNotified }
} }
fun updateLuckyNumber(luckyNumber: LuckyNumber): Completable { fun updateLuckyNumber(luckyNumber: LuckyNumber): Completable {

View File

@ -1,15 +1,22 @@
package io.github.wulkanowy.data.repositories.message package io.github.wulkanowy.data.repositories.message
import io.github.wulkanowy.data.db.dao.MessageAttachmentDao
import io.github.wulkanowy.data.db.dao.MessagesDao import io.github.wulkanowy.data.db.dao.MessagesDao
import io.github.wulkanowy.data.db.entities.Message import io.github.wulkanowy.data.db.entities.Message
import io.github.wulkanowy.data.db.entities.MessageAttachment
import io.github.wulkanowy.data.db.entities.MessageWithAttachment
import io.github.wulkanowy.data.db.entities.Student import io.github.wulkanowy.data.db.entities.Student
import io.github.wulkanowy.data.repositories.message.MessageFolder.TRASHED import io.github.wulkanowy.data.repositories.message.MessageFolder.TRASHED
import io.reactivex.Maybe import io.reactivex.Maybe
import io.reactivex.Single
import javax.inject.Inject import javax.inject.Inject
import javax.inject.Singleton import javax.inject.Singleton
@Singleton @Singleton
class MessageLocal @Inject constructor(private val messagesDb: MessagesDao) { class MessageLocal @Inject constructor(
private val messagesDb: MessagesDao,
private val messageAttachmentDao: MessageAttachmentDao
) {
fun saveMessages(messages: List<Message>) { fun saveMessages(messages: List<Message>) {
messagesDb.insertAll(messages) messagesDb.insertAll(messages)
@ -23,8 +30,12 @@ class MessageLocal @Inject constructor(private val messagesDb: MessagesDao) {
messagesDb.deleteAll(messages) messagesDb.deleteAll(messages)
} }
fun getMessage(id: Long): Maybe<Message> { fun getMessageWithAttachment(student: Student, message: Message): Single<MessageWithAttachment> {
return messagesDb.load(id) return messagesDb.loadMessageWithAttachment(student.id.toInt(), message.messageId)
}
fun saveMessageAttachments(attachments: List<MessageAttachment>) {
messageAttachmentDao.insertAttachments(attachments)
} }
fun getMessages(student: Student, folder: MessageFolder): Maybe<List<Message>> { fun getMessages(student: Student, folder: MessageFolder): Maybe<List<Message>> {

View File

@ -1,12 +1,14 @@
package io.github.wulkanowy.data.repositories.message package io.github.wulkanowy.data.repositories.message
import io.github.wulkanowy.data.db.entities.Message import io.github.wulkanowy.data.db.entities.Message
import io.github.wulkanowy.data.db.entities.MessageAttachment
import io.github.wulkanowy.data.db.entities.Recipient import io.github.wulkanowy.data.db.entities.Recipient
import io.github.wulkanowy.data.db.entities.Semester import io.github.wulkanowy.data.db.entities.Semester
import io.github.wulkanowy.data.db.entities.Student import io.github.wulkanowy.data.db.entities.Student
import io.github.wulkanowy.sdk.Sdk import io.github.wulkanowy.sdk.Sdk
import io.github.wulkanowy.sdk.pojo.Folder import io.github.wulkanowy.sdk.pojo.Folder
import io.github.wulkanowy.sdk.pojo.SentMessage import io.github.wulkanowy.sdk.pojo.SentMessage
import io.github.wulkanowy.utils.init
import io.reactivex.Single import io.reactivex.Single
import org.threeten.bp.LocalDateTime.now import org.threeten.bp.LocalDateTime.now
import javax.inject.Inject import javax.inject.Inject
@ -17,7 +19,7 @@ import io.github.wulkanowy.sdk.pojo.Recipient as SdkRecipient
class MessageRemote @Inject constructor(private val sdk: Sdk) { class MessageRemote @Inject constructor(private val sdk: Sdk) {
fun getMessages(student: Student, semester: Semester, folder: MessageFolder): Single<List<Message>> { fun getMessages(student: Student, semester: Semester, folder: MessageFolder): Single<List<Message>> {
return sdk.getMessages(Folder.valueOf(folder.name), semester.start.atStartOfDay(), semester.end.atStartOfDay()).map { messages -> return sdk.init(student).getMessages(Folder.valueOf(folder.name), semester.start.atStartOfDay(), semester.end.atStartOfDay()).map { messages ->
messages.map { messages.map {
Message( Message(
studentId = student.id.toInt(), studentId = student.id.toInt(),
@ -33,18 +35,29 @@ class MessageRemote @Inject constructor(private val sdk: Sdk) {
unread = it.unread ?: false, unread = it.unread ?: false,
unreadBy = it.unreadBy ?: 0, unreadBy = it.unreadBy ?: 0,
readBy = it.readBy ?: 0, readBy = it.readBy ?: 0,
removed = it.removed removed = it.removed,
hasAttachments = it.hasAttachments
) )
} }
} }
} }
fun getMessagesContent(message: Message, markAsRead: Boolean = false): Single<String> { fun getMessagesContentDetails(student: Student, message: Message, markAsRead: Boolean = false): Single<Pair<String, List<MessageAttachment>>> {
return sdk.getMessageContent(message.messageId, message.folderId, markAsRead, message.realId) return sdk.init(student).getMessageDetails(message.messageId, message.folderId, markAsRead, message.realId).map { details ->
details.content to details.attachments.map {
MessageAttachment(
realId = it.id,
messageId = it.messageId,
oneDriveId = it.oneDriveId,
url = it.url,
filename = it.filename
)
}
}
} }
fun sendMessage(subject: String, content: String, recipients: List<Recipient>): Single<SentMessage> { fun sendMessage(student: Student, subject: String, content: String, recipients: List<Recipient>): Single<SentMessage> {
return sdk.sendMessage( return sdk.init(student).sendMessage(
subject = subject, subject = subject,
content = content, content = content,
recipients = recipients.map { recipients = recipients.map {
@ -61,7 +74,7 @@ class MessageRemote @Inject constructor(private val sdk: Sdk) {
) )
} }
fun deleteMessage(message: Message): Single<Boolean> { fun deleteMessage(student: Student, message: Message): Single<Boolean> {
return sdk.deleteMessages(listOf(Pair(message.realId, message.folderId))) return sdk.init(student).deleteMessages(listOf(Pair(message.realId, message.folderId)))
} }
} }

View File

@ -2,8 +2,8 @@ package io.github.wulkanowy.data.repositories.message
import com.github.pwittchen.reactivenetwork.library.rx2.ReactiveNetwork import com.github.pwittchen.reactivenetwork.library.rx2.ReactiveNetwork
import com.github.pwittchen.reactivenetwork.library.rx2.internet.observing.InternetObservingSettings import com.github.pwittchen.reactivenetwork.library.rx2.internet.observing.InternetObservingSettings
import io.github.wulkanowy.data.SdkHelper
import io.github.wulkanowy.data.db.entities.Message import io.github.wulkanowy.data.db.entities.Message
import io.github.wulkanowy.data.db.entities.MessageWithAttachment
import io.github.wulkanowy.data.db.entities.Recipient import io.github.wulkanowy.data.db.entities.Recipient
import io.github.wulkanowy.data.db.entities.Semester import io.github.wulkanowy.data.db.entities.Semester
import io.github.wulkanowy.data.db.entities.Student import io.github.wulkanowy.data.db.entities.Student
@ -11,8 +11,8 @@ import io.github.wulkanowy.data.repositories.message.MessageFolder.RECEIVED
import io.github.wulkanowy.sdk.pojo.SentMessage import io.github.wulkanowy.sdk.pojo.SentMessage
import io.github.wulkanowy.utils.uniqueSubtract import io.github.wulkanowy.utils.uniqueSubtract
import io.reactivex.Completable import io.reactivex.Completable
import io.reactivex.Maybe
import io.reactivex.Single import io.reactivex.Single
import timber.log.Timber
import java.net.UnknownHostException import java.net.UnknownHostException
import javax.inject.Inject import javax.inject.Inject
import javax.inject.Singleton import javax.inject.Singleton
@ -21,14 +21,11 @@ import javax.inject.Singleton
class MessageRepository @Inject constructor( class MessageRepository @Inject constructor(
private val settings: InternetObservingSettings, private val settings: InternetObservingSettings,
private val local: MessageLocal, private val local: MessageLocal,
private val remote: MessageRemote, private val remote: MessageRemote
private val sdkHelper: SdkHelper
) { ) {
fun getMessages(student: Student, semester: Semester, folder: MessageFolder, forceRefresh: Boolean = false, notify: Boolean = false): Single<List<Message>> { fun getMessages(student: Student, semester: Semester, folder: MessageFolder, forceRefresh: Boolean = false, notify: Boolean = false): Single<List<Message>> {
return Single.just(sdkHelper.init(student)) return local.getMessages(student, folder).filter { !forceRefresh }
.flatMap { _ ->
local.getMessages(student, folder).filter { !forceRefresh }
.switchIfEmpty(ReactiveNetwork.checkInternetConnectivity(settings) .switchIfEmpty(ReactiveNetwork.checkInternetConnectivity(settings)
.flatMap { .flatMap {
if (it) remote.getMessages(student, semester, folder) if (it) remote.getMessages(student, semester, folder)
@ -45,31 +42,33 @@ class MessageRepository @Inject constructor(
}.flatMap { local.getMessages(student, folder).toSingle(emptyList()) } }.flatMap { local.getMessages(student, folder).toSingle(emptyList()) }
) )
} }
}
fun getMessage(student: Student, messageDbId: Long, markAsRead: Boolean = false): Single<Message> { fun getMessage(student: Student, message: Message, markAsRead: Boolean = false): Single<MessageWithAttachment> {
return Single.just(sdkHelper.init(student)) return local.getMessageWithAttachment(student, message)
.flatMap { _ -> .filter {
local.getMessage(messageDbId) it.message.content.isNotEmpty().also { status ->
.filter { it.content.isNotEmpty() } Timber.d("Message content in db empty: ${!status}")
} && !it.message.unread
}
.switchIfEmpty(ReactiveNetwork.checkInternetConnectivity(settings) .switchIfEmpty(ReactiveNetwork.checkInternetConnectivity(settings)
.flatMap { .flatMap {
if (it) local.getMessage(messageDbId).toSingle() if (it) local.getMessageWithAttachment(student, message)
else Single.error(UnknownHostException()) else Single.error(UnknownHostException())
} }
.flatMap { dbMessage -> .flatMap { dbMessage ->
remote.getMessagesContent(dbMessage, markAsRead).doOnSuccess { remote.getMessagesContentDetails(student, dbMessage.message, markAsRead).doOnSuccess { (downloadedMessage, attachments) ->
local.updateMessages(listOf(dbMessage.copy(unread = false).apply { local.updateMessages(listOf(dbMessage.message.copy(unread = !markAsRead).apply {
id = dbMessage.id id = dbMessage.message.id
content = content.ifBlank { it } content = content.ifBlank { downloadedMessage }
})) }))
local.saveMessageAttachments(attachments)
Timber.d("Message ${message.messageId} with blank content: ${dbMessage.message.content.isBlank()}, marked as read")
} }
}.flatMap { }.flatMap {
local.getMessage(messageDbId).toSingle() local.getMessageWithAttachment(student, message)
} }
) )
} }
}
fun getNotNotifiedMessages(student: Student): Single<List<Message>> { fun getNotNotifiedMessages(student: Student): Single<List<Message>> {
return local.getMessages(student, RECEIVED) return local.getMessages(student, RECEIVED)
@ -77,29 +76,24 @@ class MessageRepository @Inject constructor(
.toSingle(emptyList()) .toSingle(emptyList())
} }
fun updateMessage(message: Message): Completable {
return Completable.fromCallable { local.updateMessages(listOf(message)) }
}
fun updateMessages(messages: List<Message>): Completable { fun updateMessages(messages: List<Message>): Completable {
return Completable.fromCallable { local.updateMessages(messages) } return Completable.fromCallable { local.updateMessages(messages) }
} }
fun sendMessage(subject: String, content: String, recipients: List<Recipient>): Single<SentMessage> { fun sendMessage(student: Student, subject: String, content: String, recipients: List<Recipient>): Single<SentMessage> {
return ReactiveNetwork.checkInternetConnectivity(settings) return ReactiveNetwork.checkInternetConnectivity(settings)
.flatMap { .flatMap {
if (it) remote.sendMessage(subject, content, recipients) if (it) remote.sendMessage(student, subject, content, recipients)
else Single.error(UnknownHostException()) else Single.error(UnknownHostException())
} }
} }
fun deleteMessage(message: Message): Maybe<Boolean> { fun deleteMessage(student: Student, message: Message): Single<Boolean> {
return ReactiveNetwork.checkInternetConnectivity(settings) return ReactiveNetwork.checkInternetConnectivity(settings)
.flatMap { .flatMap {
if (it) remote.deleteMessage(message) if (it) remote.deleteMessage(student, message)
else Single.error(UnknownHostException()) else Single.error(UnknownHostException())
} }
.filter { it }
.doOnSuccess { .doOnSuccess {
if (!message.removed) local.updateMessages(listOf(message.copy(removed = true).apply { if (!message.removed) local.updateMessages(listOf(message.copy(removed = true).apply {
id = message.id id = message.id

View File

@ -2,8 +2,10 @@ package io.github.wulkanowy.data.repositories.mobiledevice
import io.github.wulkanowy.data.db.entities.MobileDevice import io.github.wulkanowy.data.db.entities.MobileDevice
import io.github.wulkanowy.data.db.entities.Semester import io.github.wulkanowy.data.db.entities.Semester
import io.github.wulkanowy.data.db.entities.Student
import io.github.wulkanowy.data.pojos.MobileDeviceToken import io.github.wulkanowy.data.pojos.MobileDeviceToken
import io.github.wulkanowy.sdk.Sdk import io.github.wulkanowy.sdk.Sdk
import io.github.wulkanowy.utils.init
import io.reactivex.Single import io.reactivex.Single
import javax.inject.Inject import javax.inject.Inject
import javax.inject.Singleton import javax.inject.Singleton
@ -11,13 +13,14 @@ import javax.inject.Singleton
@Singleton @Singleton
class MobileDeviceRemote @Inject constructor(private val sdk: Sdk) { class MobileDeviceRemote @Inject constructor(private val sdk: Sdk) {
fun getDevices(semester: Semester): Single<List<MobileDevice>> { fun getDevices(student: Student, semester: Semester): Single<List<MobileDevice>> {
return sdk.switchDiary(semester.diaryId, semester.schoolYear).getRegisteredDevices() return sdk.init(student).switchDiary(semester.diaryId, semester.schoolYear)
.getRegisteredDevices()
.map { devices -> .map { devices ->
devices.map { devices.map {
MobileDevice( MobileDevice(
studentId = semester.studentId, studentId = semester.studentId,
date = it.date, date = it.createDate,
deviceId = it.id, deviceId = it.id,
name = it.name name = it.name
) )
@ -25,12 +28,14 @@ class MobileDeviceRemote @Inject constructor(private val sdk: Sdk) {
} }
} }
fun unregisterDevice(semester: Semester, device: MobileDevice): Single<Boolean> { fun unregisterDevice(student: Student, semester: Semester, device: MobileDevice): Single<Boolean> {
return sdk.switchDiary(semester.diaryId, semester.schoolYear).unregisterDevice(device.deviceId) return sdk.init(student).switchDiary(semester.diaryId, semester.schoolYear)
.unregisterDevice(device.deviceId)
} }
fun getToken(semester: Semester): Single<MobileDeviceToken> { fun getToken(student: Student, semester: Semester): Single<MobileDeviceToken> {
return sdk.switchDiary(semester.diaryId, semester.schoolYear).getToken() return sdk.init(student).switchDiary(semester.diaryId, semester.schoolYear)
.getToken()
.map { .map {
MobileDeviceToken( MobileDeviceToken(
token = it.token, token = it.token,

View File

@ -4,6 +4,7 @@ import com.github.pwittchen.reactivenetwork.library.rx2.ReactiveNetwork
import com.github.pwittchen.reactivenetwork.library.rx2.internet.observing.InternetObservingSettings import com.github.pwittchen.reactivenetwork.library.rx2.internet.observing.InternetObservingSettings
import io.github.wulkanowy.data.db.entities.MobileDevice import io.github.wulkanowy.data.db.entities.MobileDevice
import io.github.wulkanowy.data.db.entities.Semester import io.github.wulkanowy.data.db.entities.Semester
import io.github.wulkanowy.data.db.entities.Student
import io.github.wulkanowy.data.pojos.MobileDeviceToken import io.github.wulkanowy.data.pojos.MobileDeviceToken
import io.github.wulkanowy.utils.uniqueSubtract import io.github.wulkanowy.utils.uniqueSubtract
import io.reactivex.Single import io.reactivex.Single
@ -18,11 +19,11 @@ class MobileDeviceRepository @Inject constructor(
private val remote: MobileDeviceRemote private val remote: MobileDeviceRemote
) { ) {
fun getDevices(semester: Semester, forceRefresh: Boolean = false): Single<List<MobileDevice>> { fun getDevices(student: Student, semester: Semester, forceRefresh: Boolean = false): Single<List<MobileDevice>> {
return local.getDevices(semester).filter { !forceRefresh } return local.getDevices(semester).filter { !forceRefresh }
.switchIfEmpty(ReactiveNetwork.checkInternetConnectivity(settings) .switchIfEmpty(ReactiveNetwork.checkInternetConnectivity(settings)
.flatMap { .flatMap {
if (it) remote.getDevices(semester) if (it) remote.getDevices(student, semester)
else Single.error(UnknownHostException()) else Single.error(UnknownHostException())
}.flatMap { new -> }.flatMap { new ->
local.getDevices(semester).toSingle(emptyList()) local.getDevices(semester).toSingle(emptyList())
@ -34,18 +35,18 @@ class MobileDeviceRepository @Inject constructor(
).flatMap { local.getDevices(semester).toSingle(emptyList()) } ).flatMap { local.getDevices(semester).toSingle(emptyList()) }
} }
fun unregisterDevice(semester: Semester, device: MobileDevice): Single<Boolean> { fun unregisterDevice(student: Student, semester: Semester, device: MobileDevice): Single<Boolean> {
return ReactiveNetwork.checkInternetConnectivity(settings) return ReactiveNetwork.checkInternetConnectivity(settings)
.flatMap { .flatMap {
if (it) remote.unregisterDevice(semester, device) if (it) remote.unregisterDevice(student, semester, device)
else Single.error(UnknownHostException()) else Single.error(UnknownHostException())
} }
} }
fun getToken(semester: Semester): Single<MobileDeviceToken> { fun getToken(student: Student, semester: Semester): Single<MobileDeviceToken> {
return ReactiveNetwork.checkInternetConnectivity(settings) return ReactiveNetwork.checkInternetConnectivity(settings)
.flatMap { .flatMap {
if (it) remote.getToken(semester) if (it) remote.getToken(student, semester)
else Single.error(UnknownHostException()) else Single.error(UnknownHostException())
} }
} }

View File

@ -2,7 +2,9 @@ package io.github.wulkanowy.data.repositories.note
import io.github.wulkanowy.data.db.entities.Note import io.github.wulkanowy.data.db.entities.Note
import io.github.wulkanowy.data.db.entities.Semester import io.github.wulkanowy.data.db.entities.Semester
import io.github.wulkanowy.data.db.entities.Student
import io.github.wulkanowy.sdk.Sdk import io.github.wulkanowy.sdk.Sdk
import io.github.wulkanowy.utils.init
import io.reactivex.Single import io.reactivex.Single
import javax.inject.Inject import javax.inject.Inject
import javax.inject.Singleton import javax.inject.Singleton
@ -10,15 +12,20 @@ import javax.inject.Singleton
@Singleton @Singleton
class NoteRemote @Inject constructor(private val sdk: Sdk) { class NoteRemote @Inject constructor(private val sdk: Sdk) {
fun getNotes(semester: Semester): Single<List<Note>> { fun getNotes(student: Student, semester: Semester): Single<List<Note>> {
return sdk.switchDiary(semester.diaryId, semester.schoolYear).getNotes(semester.semesterId) return sdk.init(student).switchDiary(semester.diaryId, semester.schoolYear)
.getNotes(semester.semesterId)
.map { notes -> .map { notes ->
notes.map { notes.map {
Note( Note(
studentId = semester.studentId, studentId = semester.studentId,
date = it.date, date = it.date,
teacher = it.teacher, teacher = it.teacher,
teacherSymbol = it.teacherSymbol,
category = it.category, category = it.category,
categoryType = it.categoryType.id,
isPointsShow = it.showPoints,
points = it.points,
content = it.content content = it.content
) )
} }

View File

@ -23,7 +23,7 @@ class NoteRepository @Inject constructor(
return local.getNotes(student).filter { !forceRefresh } return local.getNotes(student).filter { !forceRefresh }
.switchIfEmpty(ReactiveNetwork.checkInternetConnectivity(settings) .switchIfEmpty(ReactiveNetwork.checkInternetConnectivity(settings)
.flatMap { .flatMap {
if (it) remote.getNotes(semester) if (it) remote.getNotes(student, semester)
else Single.error(UnknownHostException()) else Single.error(UnknownHostException())
}.flatMap { new -> }.flatMap { new ->
local.getNotes(student).toSingle(emptyList()) local.getNotes(student).toSingle(emptyList())

View File

@ -3,7 +3,9 @@ package io.github.wulkanowy.data.repositories.recipient
import io.github.wulkanowy.data.db.entities.Message import io.github.wulkanowy.data.db.entities.Message
import io.github.wulkanowy.data.db.entities.Recipient import io.github.wulkanowy.data.db.entities.Recipient
import io.github.wulkanowy.data.db.entities.ReportingUnit import io.github.wulkanowy.data.db.entities.ReportingUnit
import io.github.wulkanowy.data.db.entities.Student
import io.github.wulkanowy.sdk.Sdk import io.github.wulkanowy.sdk.Sdk
import io.github.wulkanowy.utils.init
import io.reactivex.Single import io.reactivex.Single
import javax.inject.Inject import javax.inject.Inject
import javax.inject.Singleton import javax.inject.Singleton
@ -12,15 +14,15 @@ import io.github.wulkanowy.sdk.pojo.Recipient as SdkRecipient
@Singleton @Singleton
class RecipientRemote @Inject constructor(private val sdk: Sdk) { class RecipientRemote @Inject constructor(private val sdk: Sdk) {
fun getRecipients(role: Int, unit: ReportingUnit): Single<List<Recipient>> { fun getRecipients(student: Student, role: Int, unit: ReportingUnit): Single<List<Recipient>> {
return sdk.getRecipients(unit.realId, role) return sdk.init(student).getRecipients(unit.realId, role)
.map { recipients -> .map { recipients ->
recipients.map { it.toRecipient() } recipients.map { it.toRecipient() }
} }
} }
fun getMessageRecipients(message: Message): Single<List<Recipient>> { fun getMessageRecipients(student: Student, message: Message): Single<List<Recipient>> {
return sdk.getMessageRecipients(message.messageId, message.senderId) return sdk.init(student).getMessageRecipients(message.messageId, message.senderId)
.map { recipients -> .map { recipients ->
recipients.map { it.toRecipient() } recipients.map { it.toRecipient() }
} }

View File

@ -2,7 +2,6 @@ package io.github.wulkanowy.data.repositories.recipient
import com.github.pwittchen.reactivenetwork.library.rx2.ReactiveNetwork import com.github.pwittchen.reactivenetwork.library.rx2.ReactiveNetwork
import com.github.pwittchen.reactivenetwork.library.rx2.internet.observing.InternetObservingSettings import com.github.pwittchen.reactivenetwork.library.rx2.internet.observing.InternetObservingSettings
import io.github.wulkanowy.data.SdkHelper
import io.github.wulkanowy.data.db.entities.Message import io.github.wulkanowy.data.db.entities.Message
import io.github.wulkanowy.data.db.entities.Recipient import io.github.wulkanowy.data.db.entities.Recipient
import io.github.wulkanowy.data.db.entities.ReportingUnit import io.github.wulkanowy.data.db.entities.ReportingUnit
@ -17,17 +16,14 @@ import javax.inject.Singleton
class RecipientRepository @Inject constructor( class RecipientRepository @Inject constructor(
private val settings: InternetObservingSettings, private val settings: InternetObservingSettings,
private val local: RecipientLocal, private val local: RecipientLocal,
private val remote: RecipientRemote, private val remote: RecipientRemote
private val sdkHelper: SdkHelper
) { ) {
fun getRecipients(student: Student, role: Int, unit: ReportingUnit, forceRefresh: Boolean = false): Single<List<Recipient>> { fun getRecipients(student: Student, role: Int, unit: ReportingUnit, forceRefresh: Boolean = false): Single<List<Recipient>> {
return Single.just(sdkHelper.init(student)) return local.getRecipients(student, role, unit).filter { !forceRefresh }
.flatMap { _ ->
local.getRecipients(student, role, unit).filter { !forceRefresh }
.switchIfEmpty(ReactiveNetwork.checkInternetConnectivity(settings) .switchIfEmpty(ReactiveNetwork.checkInternetConnectivity(settings)
.flatMap { .flatMap {
if (it) remote.getRecipients(role, unit) if (it) remote.getRecipients(student, role, unit)
else Single.error(UnknownHostException()) else Single.error(UnknownHostException())
}.flatMap { new -> }.flatMap { new ->
local.getRecipients(student, role, unit).toSingle(emptyList()) local.getRecipients(student, role, unit).toSingle(emptyList())
@ -40,13 +36,11 @@ class RecipientRepository @Inject constructor(
} }
) )
} }
}
fun getMessageRecipients(student: Student, message: Message): Single<List<Recipient>> { fun getMessageRecipients(student: Student, message: Message): Single<List<Recipient>> {
return Single.just(sdkHelper.init(student)) return ReactiveNetwork.checkInternetConnectivity(settings)
.flatMap { ReactiveNetwork.checkInternetConnectivity(settings) }
.flatMap { .flatMap {
if (it) remote.getMessageRecipients(message) if (it) remote.getMessageRecipients(student, message)
else Single.error(UnknownHostException()) else Single.error(UnknownHostException())
} }
} }

View File

@ -0,0 +1,19 @@
package io.github.wulkanowy.data.repositories.recover
import io.github.wulkanowy.sdk.Sdk
import io.reactivex.Single
import javax.inject.Inject
import javax.inject.Singleton
@Singleton
class RecoverRemote @Inject constructor(private val sdk: Sdk) {
fun getReCaptchaSiteKey(host: String, symbol: String): Single<Pair<String, String>> {
return sdk.getPasswordResetCaptchaCode(host, symbol)
}
fun sendRecoverRequest(url: String, symbol: String, email: String, reCaptchaResponse: String): Single<String> {
return sdk.sendPasswordResetRequest(url, symbol, email, reCaptchaResponse)
}
}

View File

@ -0,0 +1,26 @@
package io.github.wulkanowy.data.repositories.recover
import com.github.pwittchen.reactivenetwork.library.rx2.ReactiveNetwork
import com.github.pwittchen.reactivenetwork.library.rx2.internet.observing.InternetObservingSettings
import io.reactivex.Single
import java.net.UnknownHostException
import javax.inject.Inject
import javax.inject.Singleton
@Singleton
class RecoverRepository @Inject constructor(private val settings: InternetObservingSettings, private val remote: RecoverRemote) {
fun getReCaptchaSiteKey(host: String, symbol: String): Single<Pair<String, String>> {
return ReactiveNetwork.checkInternetConnectivity(settings).flatMap {
if (it) remote.getReCaptchaSiteKey(host, symbol)
else Single.error(UnknownHostException())
}
}
fun sendRecoverRequest(url: String, symbol: String, email: String, reCaptchaResponse: String): Single<String> {
return ReactiveNetwork.checkInternetConnectivity(settings).flatMap {
if (it) remote.sendRecoverRequest(url, symbol, email, reCaptchaResponse)
else Single.error(UnknownHostException())
}
}
}

View File

@ -1,7 +1,9 @@
package io.github.wulkanowy.data.repositories.reportingunit package io.github.wulkanowy.data.repositories.reportingunit
import io.github.wulkanowy.data.db.entities.ReportingUnit import io.github.wulkanowy.data.db.entities.ReportingUnit
import io.github.wulkanowy.data.db.entities.Student
import io.github.wulkanowy.sdk.Sdk import io.github.wulkanowy.sdk.Sdk
import io.github.wulkanowy.utils.init
import io.reactivex.Single import io.reactivex.Single
import javax.inject.Inject import javax.inject.Inject
import javax.inject.Singleton import javax.inject.Singleton
@ -9,8 +11,8 @@ import javax.inject.Singleton
@Singleton @Singleton
class ReportingUnitRemote @Inject constructor(private val sdk: Sdk) { class ReportingUnitRemote @Inject constructor(private val sdk: Sdk) {
fun getReportingUnits(): Single<List<ReportingUnit>> { fun getReportingUnits(student: Student): Single<List<ReportingUnit>> {
return sdk.getReportingUnits().map { return sdk.init(student).getReportingUnits().map {
it.map { unit -> it.map { unit ->
ReportingUnit( ReportingUnit(
studentId = sdk.studentId, studentId = sdk.studentId,

View File

@ -2,7 +2,6 @@ package io.github.wulkanowy.data.repositories.reportingunit
import com.github.pwittchen.reactivenetwork.library.rx2.ReactiveNetwork import com.github.pwittchen.reactivenetwork.library.rx2.ReactiveNetwork
import com.github.pwittchen.reactivenetwork.library.rx2.internet.observing.InternetObservingSettings import com.github.pwittchen.reactivenetwork.library.rx2.internet.observing.InternetObservingSettings
import io.github.wulkanowy.data.SdkHelper
import io.github.wulkanowy.data.db.entities.ReportingUnit import io.github.wulkanowy.data.db.entities.ReportingUnit
import io.github.wulkanowy.data.db.entities.Student import io.github.wulkanowy.data.db.entities.Student
import io.github.wulkanowy.utils.uniqueSubtract import io.github.wulkanowy.utils.uniqueSubtract
@ -16,17 +15,14 @@ import javax.inject.Singleton
class ReportingUnitRepository @Inject constructor( class ReportingUnitRepository @Inject constructor(
private val settings: InternetObservingSettings, private val settings: InternetObservingSettings,
private val local: ReportingUnitLocal, private val local: ReportingUnitLocal,
private val remote: ReportingUnitRemote, private val remote: ReportingUnitRemote
private val sdkHelper: SdkHelper
) { ) {
fun getReportingUnits(student: Student, forceRefresh: Boolean = false): Single<List<ReportingUnit>> { fun getReportingUnits(student: Student, forceRefresh: Boolean = false): Single<List<ReportingUnit>> {
return Single.just(sdkHelper.init(student)) return local.getReportingUnits(student).filter { !forceRefresh }
.flatMap { _ ->
local.getReportingUnits(student).filter { !forceRefresh }
.switchIfEmpty(ReactiveNetwork.checkInternetConnectivity(settings) .switchIfEmpty(ReactiveNetwork.checkInternetConnectivity(settings)
.flatMap { .flatMap {
if (it) remote.getReportingUnits() if (it) remote.getReportingUnits(student)
else Single.error(UnknownHostException()) else Single.error(UnknownHostException())
}.flatMap { new -> }.flatMap { new ->
local.getReportingUnits(student).toSingle(emptyList()) local.getReportingUnits(student).toSingle(emptyList())
@ -37,12 +33,9 @@ class ReportingUnitRepository @Inject constructor(
}.flatMap { local.getReportingUnits(student).toSingle(emptyList()) } }.flatMap { local.getReportingUnits(student).toSingle(emptyList()) }
) )
} }
}
fun getReportingUnit(student: Student, unitId: Int): Maybe<ReportingUnit> { fun getReportingUnit(student: Student, unitId: Int): Maybe<ReportingUnit> {
return Maybe.just(sdkHelper.init(student)) return local.getReportingUnit(student, unitId)
.flatMap { _ ->
local.getReportingUnit(student, unitId)
.switchIfEmpty(ReactiveNetwork.checkInternetConnectivity(settings) .switchIfEmpty(ReactiveNetwork.checkInternetConnectivity(settings)
.flatMap { .flatMap {
if (it) getReportingUnits(student, true) if (it) getReportingUnits(student, true)
@ -52,5 +45,4 @@ class ReportingUnitRepository @Inject constructor(
} }
) )
} }
}
} }

View File

@ -2,14 +2,17 @@ package io.github.wulkanowy.data.repositories.school
import io.github.wulkanowy.data.db.entities.School import io.github.wulkanowy.data.db.entities.School
import io.github.wulkanowy.data.db.entities.Semester import io.github.wulkanowy.data.db.entities.Semester
import io.github.wulkanowy.data.db.entities.Student
import io.github.wulkanowy.sdk.Sdk import io.github.wulkanowy.sdk.Sdk
import io.github.wulkanowy.utils.init
import io.reactivex.Single import io.reactivex.Single
import javax.inject.Inject import javax.inject.Inject
class SchoolRemote @Inject constructor(private val sdk: Sdk) { class SchoolRemote @Inject constructor(private val sdk: Sdk) {
fun getSchoolInfo(semester: Semester): Single<School> { fun getSchoolInfo(student: Student, semester: Semester): Single<School> {
return sdk.switchDiary(semester.diaryId, semester.schoolYear).getSchool() return sdk.init(student).switchDiary(semester.diaryId, semester.schoolYear)
.getSchool()
.map { .map {
School( School(
studentId = semester.studentId, studentId = semester.studentId,

View File

@ -4,6 +4,7 @@ import com.github.pwittchen.reactivenetwork.library.rx2.ReactiveNetwork
import com.github.pwittchen.reactivenetwork.library.rx2.internet.observing.InternetObservingSettings import com.github.pwittchen.reactivenetwork.library.rx2.internet.observing.InternetObservingSettings
import io.github.wulkanowy.data.db.entities.School import io.github.wulkanowy.data.db.entities.School
import io.github.wulkanowy.data.db.entities.Semester import io.github.wulkanowy.data.db.entities.Semester
import io.github.wulkanowy.data.db.entities.Student
import io.reactivex.Maybe import io.reactivex.Maybe
import io.reactivex.Single import io.reactivex.Single
import java.net.UnknownHostException import java.net.UnknownHostException
@ -17,11 +18,11 @@ class SchoolRepository @Inject constructor(
private val remote: SchoolRemote private val remote: SchoolRemote
) { ) {
fun getSchoolInfo(semester: Semester, forceRefresh: Boolean = false): Maybe<School> { fun getSchoolInfo(student: Student, semester: Semester, forceRefresh: Boolean = false): Maybe<School> {
return local.getSchool(semester).filter { !forceRefresh } return local.getSchool(semester).filter { !forceRefresh }
.switchIfEmpty(ReactiveNetwork.checkInternetConnectivity(settings) .switchIfEmpty(ReactiveNetwork.checkInternetConnectivity(settings)
.flatMap { .flatMap {
if (it) remote.getSchoolInfo(semester) if (it) remote.getSchoolInfo(student, semester)
else Single.error(UnknownHostException()) else Single.error(UnknownHostException())
}.flatMapMaybe { new -> }.flatMapMaybe { new ->
local.getSchool(semester) local.getSchool(semester)

View File

@ -19,6 +19,6 @@ class SemesterLocal @Inject constructor(private val semesterDb: SemesterDao) {
} }
fun getSemesters(student: Student): Maybe<List<Semester>> { fun getSemesters(student: Student): Maybe<List<Semester>> {
return semesterDb.loadAll(student.studentId, student.classId).filter { !it.isEmpty() } return semesterDb.loadAll(student.studentId, student.classId).filter { it.isNotEmpty() }
} }
} }

View File

@ -3,6 +3,7 @@ package io.github.wulkanowy.data.repositories.semester
import io.github.wulkanowy.data.db.entities.Semester import io.github.wulkanowy.data.db.entities.Semester
import io.github.wulkanowy.data.db.entities.Student import io.github.wulkanowy.data.db.entities.Student
import io.github.wulkanowy.sdk.Sdk import io.github.wulkanowy.sdk.Sdk
import io.github.wulkanowy.utils.init
import io.reactivex.Single import io.reactivex.Single
import javax.inject.Inject import javax.inject.Inject
import javax.inject.Singleton import javax.inject.Singleton
@ -11,7 +12,7 @@ import javax.inject.Singleton
class SemesterRemote @Inject constructor(private val sdk: Sdk) { class SemesterRemote @Inject constructor(private val sdk: Sdk) {
fun getSemesters(student: Student): Single<List<Semester>> { fun getSemesters(student: Student): Single<List<Semester>> {
return sdk.getSemesters().map { semesters -> return sdk.init(student).getSemesters().map { semesters ->
semesters.map { semesters.map {
Semester( Semester(
studentId = student.studentId, studentId = student.studentId,
@ -20,7 +21,6 @@ class SemesterRemote @Inject constructor(private val sdk: Sdk) {
schoolYear = it.schoolYear, schoolYear = it.schoolYear,
semesterId = it.semesterId, semesterId = it.semesterId,
semesterName = it.semesterNumber, semesterName = it.semesterNumber,
isCurrent = it.current,
start = it.start, start = it.start,
end = it.end, end = it.end,
classId = it.classId, classId = it.classId,

View File

@ -2,13 +2,13 @@ package io.github.wulkanowy.data.repositories.semester
import com.github.pwittchen.reactivenetwork.library.rx2.ReactiveNetwork import com.github.pwittchen.reactivenetwork.library.rx2.ReactiveNetwork
import com.github.pwittchen.reactivenetwork.library.rx2.internet.observing.InternetObservingSettings import com.github.pwittchen.reactivenetwork.library.rx2.internet.observing.InternetObservingSettings
import io.github.wulkanowy.data.SdkHelper
import io.github.wulkanowy.data.db.entities.Semester import io.github.wulkanowy.data.db.entities.Semester
import io.github.wulkanowy.data.db.entities.Student import io.github.wulkanowy.data.db.entities.Student
import io.github.wulkanowy.sdk.Sdk
import io.github.wulkanowy.utils.getCurrentOrLast
import io.github.wulkanowy.utils.isCurrent
import io.github.wulkanowy.utils.uniqueSubtract import io.github.wulkanowy.utils.uniqueSubtract
import io.reactivex.Maybe
import io.reactivex.Single import io.reactivex.Single
import timber.log.Timber
import java.net.UnknownHostException import java.net.UnknownHostException
import javax.inject.Inject import javax.inject.Inject
import javax.inject.Singleton import javax.inject.Singleton
@ -17,32 +17,31 @@ import javax.inject.Singleton
class SemesterRepository @Inject constructor( class SemesterRepository @Inject constructor(
private val remote: SemesterRemote, private val remote: SemesterRemote,
private val local: SemesterLocal, private val local: SemesterLocal,
private val settings: InternetObservingSettings, private val settings: InternetObservingSettings
private val sdkHelper: SdkHelper
) { ) {
fun getSemesters(student: Student, forceRefresh: Boolean = false): Single<List<Semester>> { fun getSemesters(student: Student, forceRefresh: Boolean = false, refreshOnNoCurrent: Boolean = false): Single<List<Semester>> {
return Maybe.just(sdkHelper.init(student)) return local.getSemesters(student).filter { !forceRefresh }.filter { semesters ->
.flatMap { local.getSemesters(student).filter { !forceRefresh } } when {
.switchIfEmpty(ReactiveNetwork.checkInternetConnectivity(settings) Sdk.Mode.valueOf(student.loginMode) != Sdk.Mode.API -> semesters.firstOrNull { it.isCurrent }?.diaryId != 0
refreshOnNoCurrent -> semesters.any { semester -> semester.isCurrent }
else -> true
}
}.switchIfEmpty(ReactiveNetwork.checkInternetConnectivity(settings)
.flatMap { .flatMap {
if (it) remote.getSemesters(student) else Single.error(UnknownHostException()) if (it) remote.getSemesters(student)
else Single.error(UnknownHostException())
}.flatMap { new -> }.flatMap { new ->
val currentSemesters = new.filter { it.isCurrent } if (new.isEmpty()) throw IllegalArgumentException("Empty semester list!")
if (currentSemesters.size == 1) {
local.getSemesters(student).toSingle(emptyList()) local.getSemesters(student).toSingle(emptyList()).doOnSuccess { old ->
.doOnSuccess { old ->
local.deleteSemesters(old.uniqueSubtract(new)) local.deleteSemesters(old.uniqueSubtract(new))
local.saveSemesters(new.uniqueSubtract(old)) local.saveSemesters(new.uniqueSubtract(old))
} }
} else {
Timber.i("Current semesters list:\n${new.joinToString(separator = "\n")}")
throw IllegalArgumentException("Current semester can be only one.")
}
}.flatMap { local.getSemesters(student).toSingle(emptyList()) }) }.flatMap { local.getSemesters(student).toSingle(emptyList()) })
} }
fun getCurrentSemester(student: Student, forceRefresh: Boolean = false): Single<Semester> { fun getCurrentSemester(student: Student, forceRefresh: Boolean = false): Single<Semester> {
return getSemesters(student, forceRefresh).map { item -> item.single { it.isCurrent } } return getSemesters(student, forceRefresh).map { it.getCurrentOrLast() }
} }
} }

View File

@ -29,10 +29,18 @@ class StudentLocal @Inject constructor(
fun getStudents(decryptPass: Boolean): Maybe<List<Student>> { fun getStudents(decryptPass: Boolean): Maybe<List<Student>> {
return studentDb.loadAll() return studentDb.loadAll()
.map { list -> list.map { it.apply { if (decryptPass) password = decrypt(password) } } } .map { list -> list.map { it.apply { if (decryptPass && Sdk.Mode.valueOf(loginMode) != Sdk.Mode.API) password = decrypt(password) } } }
.filter { it.isNotEmpty() } .filter { it.isNotEmpty() }
} }
fun getStudentById(id: Int): Maybe<Student> {
return studentDb.loadById(id).map {
it.apply {
if (Sdk.Mode.valueOf(loginMode) != Sdk.Mode.API) password = decrypt(password)
}
}
}
fun getCurrentStudent(decryptPass: Boolean): Maybe<Student> { fun getCurrentStudent(decryptPass: Boolean): Maybe<Student> {
return studentDb.loadCurrent().map { return studentDb.loadCurrent().map {
it.apply { it.apply {

View File

@ -22,6 +22,7 @@ class StudentRemote @Inject constructor(private val sdk: Sdk) {
userLoginId = student.userLoginId, userLoginId = student.userLoginId,
studentName = student.studentName, studentName = student.studentName,
schoolSymbol = student.schoolSymbol, schoolSymbol = student.schoolSymbol,
schoolShortName = student.schoolShortName,
schoolName = student.schoolName, schoolName = student.schoolName,
className = student.className, className = student.className,
classId = student.classId, classId = student.classId,

View File

@ -29,7 +29,7 @@ class StudentRepository @Inject constructor(
} }
} }
fun getStudentsScrapper(email: String, password: String, endpoint: String, symbol: String = ""): Single<List<Student>> { fun getStudentsScrapper(email: String, password: String, endpoint: String, symbol: String): Single<List<Student>> {
return ReactiveNetwork.checkInternetConnectivity(settings).flatMap { return ReactiveNetwork.checkInternetConnectivity(settings).flatMap {
if (it) remote.getStudentsScrapper(email, password, endpoint, symbol) if (it) remote.getStudentsScrapper(email, password, endpoint, symbol)
else Single.error(UnknownHostException("No internet connection")) else Single.error(UnknownHostException("No internet connection"))
@ -47,6 +47,12 @@ class StudentRepository @Inject constructor(
return local.getStudents(decryptPass).toSingle(emptyList()) return local.getStudents(decryptPass).toSingle(emptyList())
} }
fun getStudentById(id: Int): Single<Student> {
return local.getStudentById(id)
.switchIfEmpty(Maybe.error(NoCurrentStudentException()))
.toSingle()
}
fun getCurrentStudent(decryptPass: Boolean = true): Single<Student> { fun getCurrentStudent(decryptPass: Boolean = true): Single<Student> {
return local.getCurrentStudent(decryptPass) return local.getCurrentStudent(decryptPass)
.switchIfEmpty(Maybe.error(NoCurrentStudentException())) .switchIfEmpty(Maybe.error(NoCurrentStudentException()))

View File

@ -12,7 +12,7 @@ class SubjectLocal @Inject constructor(private val subjectDao: SubjectDao) {
fun getSubjects(semester: Semester): Maybe<List<Subject>> { fun getSubjects(semester: Semester): Maybe<List<Subject>> {
return subjectDao.loadAll(semester.diaryId, semester.studentId) return subjectDao.loadAll(semester.diaryId, semester.studentId)
.filter { !it.isEmpty() } .filter { it.isNotEmpty() }
} }
fun saveSubjects(subjects: List<Subject>) { fun saveSubjects(subjects: List<Subject>) {

View File

@ -1,8 +1,10 @@
package io.github.wulkanowy.data.repositories.subject package io.github.wulkanowy.data.repositories.subject
import io.github.wulkanowy.data.db.entities.Semester import io.github.wulkanowy.data.db.entities.Semester
import io.github.wulkanowy.data.db.entities.Student
import io.github.wulkanowy.data.db.entities.Subject import io.github.wulkanowy.data.db.entities.Subject
import io.github.wulkanowy.sdk.Sdk import io.github.wulkanowy.sdk.Sdk
import io.github.wulkanowy.utils.init
import io.reactivex.Single import io.reactivex.Single
import javax.inject.Inject import javax.inject.Inject
import javax.inject.Singleton import javax.inject.Singleton
@ -10,8 +12,9 @@ import javax.inject.Singleton
@Singleton @Singleton
class SubjectRemote @Inject constructor(private val sdk: Sdk) { class SubjectRemote @Inject constructor(private val sdk: Sdk) {
fun getSubjects(semester: Semester): Single<List<Subject>> { fun getSubjects(student: Student, semester: Semester): Single<List<Subject>> {
return sdk.switchDiary(semester.diaryId, semester.schoolYear).getSubjects() return sdk.init(student).switchDiary(semester.diaryId, semester.schoolYear)
.getSubjects()
.map { subjects -> .map { subjects ->
subjects.map { subjects.map {
Subject( Subject(

View File

@ -3,6 +3,7 @@ package io.github.wulkanowy.data.repositories.subject
import com.github.pwittchen.reactivenetwork.library.rx2.ReactiveNetwork import com.github.pwittchen.reactivenetwork.library.rx2.ReactiveNetwork
import com.github.pwittchen.reactivenetwork.library.rx2.internet.observing.InternetObservingSettings import com.github.pwittchen.reactivenetwork.library.rx2.internet.observing.InternetObservingSettings
import io.github.wulkanowy.data.db.entities.Semester import io.github.wulkanowy.data.db.entities.Semester
import io.github.wulkanowy.data.db.entities.Student
import io.github.wulkanowy.data.db.entities.Subject import io.github.wulkanowy.data.db.entities.Subject
import io.github.wulkanowy.utils.uniqueSubtract import io.github.wulkanowy.utils.uniqueSubtract
import io.reactivex.Single import io.reactivex.Single
@ -17,11 +18,11 @@ class SubjectRepository @Inject constructor(
private val remote: SubjectRemote private val remote: SubjectRemote
) { ) {
fun getSubjects(semester: Semester, forceRefresh: Boolean = false): Single<List<Subject>> { fun getSubjects(student: Student, semester: Semester, forceRefresh: Boolean = false): Single<List<Subject>> {
return local.getSubjects(semester).filter { !forceRefresh } return local.getSubjects(semester).filter { !forceRefresh }
.switchIfEmpty(ReactiveNetwork.checkInternetConnectivity(settings) .switchIfEmpty(ReactiveNetwork.checkInternetConnectivity(settings)
.flatMap { .flatMap {
if (it) remote.getSubjects(semester) if (it) remote.getSubjects(student, semester)
else Single.error(UnknownHostException()) else Single.error(UnknownHostException())
}.flatMap { new -> }.flatMap { new ->
local.getSubjects(semester) local.getSubjects(semester)

View File

@ -1,8 +1,10 @@
package io.github.wulkanowy.data.repositories.teacher package io.github.wulkanowy.data.repositories.teacher
import io.github.wulkanowy.data.db.entities.Semester import io.github.wulkanowy.data.db.entities.Semester
import io.github.wulkanowy.data.db.entities.Student
import io.github.wulkanowy.data.db.entities.Teacher import io.github.wulkanowy.data.db.entities.Teacher
import io.github.wulkanowy.sdk.Sdk import io.github.wulkanowy.sdk.Sdk
import io.github.wulkanowy.utils.init
import io.reactivex.Single import io.reactivex.Single
import javax.inject.Inject import javax.inject.Inject
import javax.inject.Singleton import javax.inject.Singleton
@ -10,8 +12,9 @@ import javax.inject.Singleton
@Singleton @Singleton
class TeacherRemote @Inject constructor(private val sdk: Sdk) { class TeacherRemote @Inject constructor(private val sdk: Sdk) {
fun getTeachers(semester: Semester): Single<List<Teacher>> { fun getTeachers(student: Student, semester: Semester): Single<List<Teacher>> {
return sdk.switchDiary(semester.diaryId, semester.schoolYear).getTeachers(semester.semesterId) return sdk.init(student).switchDiary(semester.diaryId, semester.schoolYear)
.getTeachers(semester.semesterId)
.map { teachers -> .map { teachers ->
teachers.map { teachers.map {
Teacher( Teacher(

View File

@ -3,6 +3,7 @@ package io.github.wulkanowy.data.repositories.teacher
import com.github.pwittchen.reactivenetwork.library.rx2.ReactiveNetwork import com.github.pwittchen.reactivenetwork.library.rx2.ReactiveNetwork
import com.github.pwittchen.reactivenetwork.library.rx2.internet.observing.InternetObservingSettings import com.github.pwittchen.reactivenetwork.library.rx2.internet.observing.InternetObservingSettings
import io.github.wulkanowy.data.db.entities.Semester import io.github.wulkanowy.data.db.entities.Semester
import io.github.wulkanowy.data.db.entities.Student
import io.github.wulkanowy.data.db.entities.Teacher import io.github.wulkanowy.data.db.entities.Teacher
import io.github.wulkanowy.utils.uniqueSubtract import io.github.wulkanowy.utils.uniqueSubtract
import io.reactivex.Single import io.reactivex.Single
@ -17,11 +18,11 @@ class TeacherRepository @Inject constructor(
private val remote: TeacherRemote private val remote: TeacherRemote
) { ) {
fun getTeachers(semester: Semester, forceRefresh: Boolean = false): Single<List<Teacher>> { fun getTeachers(student: Student, semester: Semester, forceRefresh: Boolean = false): Single<List<Teacher>> {
return local.getTeachers(semester).filter { !forceRefresh } return local.getTeachers(semester).filter { !forceRefresh }
.switchIfEmpty(ReactiveNetwork.checkInternetConnectivity(settings) .switchIfEmpty(ReactiveNetwork.checkInternetConnectivity(settings)
.flatMap { .flatMap {
if (it) remote.getTeachers(semester) if (it) remote.getTeachers(student, semester)
else Single.error(UnknownHostException()) else Single.error(UnknownHostException())
}.flatMap { new -> }.flatMap { new ->
local.getTeachers(semester).toSingle(emptyList()) local.getTeachers(semester).toSingle(emptyList())

View File

@ -1,8 +1,10 @@
package io.github.wulkanowy.data.repositories.timetable package io.github.wulkanowy.data.repositories.timetable
import io.github.wulkanowy.data.db.entities.Semester import io.github.wulkanowy.data.db.entities.Semester
import io.github.wulkanowy.data.db.entities.Student
import io.github.wulkanowy.data.db.entities.Timetable import io.github.wulkanowy.data.db.entities.Timetable
import io.github.wulkanowy.sdk.Sdk import io.github.wulkanowy.sdk.Sdk
import io.github.wulkanowy.utils.init
import io.reactivex.Single import io.reactivex.Single
import org.threeten.bp.LocalDate import org.threeten.bp.LocalDate
import javax.inject.Inject import javax.inject.Inject
@ -11,8 +13,9 @@ import javax.inject.Singleton
@Singleton @Singleton
class TimetableRemote @Inject constructor(private val sdk: Sdk) { class TimetableRemote @Inject constructor(private val sdk: Sdk) {
fun getTimetable(semester: Semester, startDate: LocalDate, endDate: LocalDate): Single<List<Timetable>> { fun getTimetable(student: Student, semester: Semester, startDate: LocalDate, endDate: LocalDate): Single<List<Timetable>> {
return sdk.switchDiary(semester.diaryId, semester.schoolYear).getTimetable(startDate, endDate) return sdk.init(student).switchDiary(semester.diaryId, semester.schoolYear)
.getTimetable(startDate, endDate)
.map { lessons -> .map { lessons ->
lessons.map { lessons.map {
Timetable( Timetable(
@ -30,7 +33,7 @@ class TimetableRemote @Inject constructor(private val sdk: Sdk) {
teacher = it.teacher, teacher = it.teacher,
teacherOld = it.teacherOld, teacherOld = it.teacherOld,
info = it.info, info = it.info,
studentPlan = it.studentPlan, isStudentPlan = it.studentPlan,
changes = it.changes, changes = it.changes,
canceled = it.canceled canceled = it.canceled
) )

View File

@ -3,6 +3,7 @@ package io.github.wulkanowy.data.repositories.timetable
import com.github.pwittchen.reactivenetwork.library.rx2.ReactiveNetwork import com.github.pwittchen.reactivenetwork.library.rx2.ReactiveNetwork
import com.github.pwittchen.reactivenetwork.library.rx2.internet.observing.InternetObservingSettings import com.github.pwittchen.reactivenetwork.library.rx2.internet.observing.InternetObservingSettings
import io.github.wulkanowy.data.db.entities.Semester import io.github.wulkanowy.data.db.entities.Semester
import io.github.wulkanowy.data.db.entities.Student
import io.github.wulkanowy.data.db.entities.Timetable import io.github.wulkanowy.data.db.entities.Timetable
import io.github.wulkanowy.utils.friday import io.github.wulkanowy.utils.friday
import io.github.wulkanowy.utils.monday import io.github.wulkanowy.utils.monday
@ -20,11 +21,11 @@ class TimetableRepository @Inject constructor(
private val remote: TimetableRemote private val remote: TimetableRemote
) { ) {
fun getTimetable(semester: Semester, start: LocalDate, end: LocalDate, forceRefresh: Boolean = false): Single<List<Timetable>> { fun getTimetable(student: Student, semester: Semester, start: LocalDate, end: LocalDate, forceRefresh: Boolean = false): Single<List<Timetable>> {
return Single.fromCallable { start.monday to end.friday }.flatMap { (monday, friday) -> return Single.fromCallable { start.monday to end.friday }.flatMap { (monday, friday) ->
local.getTimetable(semester, monday, friday).filter { !forceRefresh } local.getTimetable(semester, monday, friday).filter { !forceRefresh }
.switchIfEmpty(ReactiveNetwork.checkInternetConnectivity(settings).flatMap { .switchIfEmpty(ReactiveNetwork.checkInternetConnectivity(settings).flatMap {
if (it) remote.getTimetable(semester, monday, friday) if (it) remote.getTimetable(student, semester, monday, friday)
else Single.error(UnknownHostException()) else Single.error(UnknownHostException())
}.flatMap { new -> }.flatMap { new ->
local.getTimetable(semester, monday, friday) local.getTimetable(semester, monday, friday)

Some files were not shown because too many files have changed in this diff Show More