Skip to content

Commit

Permalink
Stream Episode 17: Initial SharedPreferences storage implementation (#81
Browse files Browse the repository at this point in the history
)

* Scaffold sharedpreferences module

- Attach to store implemetnation
- Mock data currently being returned

Some housekeeping.

* Small configurations for CI

Still not working, wanted to make mock work with debug but variants still compain.

* Test removing ViewModelModule

* Ci why you no work?

* Fix lints on CI

* Working stuff for CI

* housekeeping mobile-ui/build.gradle

Had to make some changtes while debuging CI fails. This change still makes sense IMO.

#69

* Rename data package to include project name
#69

* Remove unecessary .gitignore from other packages

Maintenece commit, not really related to this branch feature.

* Manifest cleanup and format

* Scaffold stuff for stream episode 17

Some basic ideas just so I know what I'm supposed to continue, a lot of TODOs
so lint warns me.

For #17
Ref #69

* Housekeeping from previous commit

* Fix typo in readme

Changed the copy on the stream log section

* Include kotlinx.serialization experimental library for sharedPrefs

This will be included in the stblib from Kotlin 1.3.

#17, #69

* Make SharedPrefTransport model @kotlinx.serialization.Serializable

Also, fixes and issue where the String was default to  which made the serialization fail:
 - Kotlin/kotlinx.serialization#115

#17, #69

* SharedPrefMapper tests

- Created necessary factory/mock data classes for the SharedPref module

Named the mock classes with the SharedPref prefix for #66

#17 #69

* Initial tests for FrameworkLocalStorageImpl

Lacking SharedPreferences test setup
  - Will probably need to move all the Android test libs to androidx variant.

#17 #69

* Include stream episode PR to README
  • Loading branch information
JoaquimLey authored Oct 17, 2018
1 parent dfb2163 commit 2d10258
Show file tree
Hide file tree
Showing 21 changed files with 530 additions and 63 deletions.
17 changes: 10 additions & 7 deletions README.MD
Original file line number Diff line number Diff line change
Expand Up @@ -2,12 +2,13 @@

<a alt='Watch the Stream' href='https://twitch.tv/joaquimley' target='_blank' align='left'><img align='right' height='50' style='border:0px;height:50px;' src='art/follow_me_twitch_badge.png?v=0' border='0' /></a>

<a alt='Available soon' href='' target='_blank' align='left'><img align='right' height='36' style='border:0px;height:36px;' src='art/googleplay_soon.png?v=0' border='0' /></a>
<a alt='Available soon' align='left'><img align='right' height='36' style='border:0px;height:36px;' src='art/googleplay_soon.png?v=0' border='0' /></a>

# Transport ETA
[![License Apache 2.0](https://img.shields.io/badge/License-Apache%202.0-blue.svg?style=true)](http://www.apache.org/licenses/LICENSE-2.0)

![production version](https://img.shields.io/badge/playstore-unreleased-lightgrey.svg?style=true)
![minSdkVersion 19](https://img.shields.io/badge/minSdkVersion-19-yellow.svg?style=true)
![compileSdkVersion 27](https://img.shields.io/badge/compileSdkVersion-28-green.svg?style=true)
![compileSdkVersion 28](https://img.shields.io/badge/compileSdkVersion-28-green.svg?style=true)
[![Build Status](https://app.bitrise.io/app/f75916759d698e6e/status.svg?token=nCaNQBZcMNPMckWWwn8Gxg&branch=develop)](https://app.bitrise.io/app/f75916759d698e6e)
[![codecov](https://codecov.io/gh/JoaquimLey/transport-eta/branch/develop/graph/badge.svg)](https://codecov.io/gh/JoaquimLey/transport-eta)

Expand All @@ -28,8 +29,8 @@ An utility app using an SMS based service (or the web) to request a more precise
## Why 🤔
Since I'm always working on some side-projects, I decided to document the progress live on a coding stream, this way I'll force myself into completing, while giving something back to a community that already thought me so much.

## Stream log
##### Come and say Hi 👋, join me at [twitch.tv/joaquimley](http:twitch.tv/joaquimley): watch, help, and learn as I develop and make mistakes
## Stream PR log
##### Come and say Hi 👋 and be part of the develpoment live at [twitch.tv/joaquimley](http:twitch.tv/joaquimley)

- Ep.1: https://github.com/JoaquimLey/transport-eta/tree/4642c5fd6af9de3b258b179d0a7a8c69195fa293

Expand Down Expand Up @@ -61,7 +62,9 @@ Since I'm always working on some side-projects, I decided to document the progre

- Ep.15: https://github.com/JoaquimLey/transport-eta/pull/70

- Ep.15: https://github.com/JoaquimLey/transport-eta/pull/74
- Ep.16: https://github.com/JoaquimLey/transport-eta/pull/74

- Ep.17: https://github.com/JoaquimLey/transport-eta/pull/81


## About the author
Expand Down Expand Up @@ -92,7 +95,7 @@ Personal website:

#### Important references

It would take substantially more time to setup this project without this reference projects
It would take substantially more time to setup this project without this reference projects, so a special thanks to:

- https://github.com/bufferapp/clean-architecture-components-boilerplate

Expand Down
4 changes: 1 addition & 3 deletions transport-eta-android/build.gradle
Original file line number Diff line number Diff line change
Expand Up @@ -4,12 +4,10 @@ buildscript {
addRepos(repositories)
dependencies {
classpath deps.kotlin.plugin
classpath deps.kotlin.serialization_plugin
classpath deps.navigation.safe_args
classpath deps.android_gradle_plugin
}
repositories {
google()
}
}

allprojects {
Expand Down
10 changes: 10 additions & 0 deletions transport-eta-android/data-sharedpreferences/build.gradle
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
apply plugin: 'com.android.library'
apply plugin: 'kotlin-kapt'
apply plugin: 'kotlinx-serialization'
apply plugin: 'kotlin-android'
apply plugin: 'kotlin-android-extensions'

Expand All @@ -11,6 +12,12 @@ android {
testInstrumentationRunner "com.joaquimley.transporteta.ui.test.TestRunner"
}

testOptions {
unitTests {
includeAndroidResources = true
}
}

packagingOptions {
exclude 'LICENSE.txt'
exclude 'META-INF/DEPENDENCIES'
Expand Down Expand Up @@ -90,6 +97,7 @@ dependencies {
implementation deps.rx.android
// Kotlin
implementation deps.kotlin.rx
implementation deps.kotlin.serialization
implementation deps.kotlin.stdlib

/***********
Expand All @@ -102,6 +110,8 @@ dependencies {
testImplementation deps.mockito.kotlin
testImplementation deps.mockito.inline
testImplementation deps.lifecycle.testing
testImplementation deps.robolectric

// Resolve conflicts between main and local unit tests
testImplementation deps.androidx.annotation
}
17 changes: 10 additions & 7 deletions transport-eta-android/data-sharedpreferences/proguard-rules.pro
Original file line number Diff line number Diff line change
Expand Up @@ -5,17 +5,20 @@
# For more details, see
# http://developer.android.com/guide/developing/tools/proguard.html

# If your project uses WebView with JS, uncomment the following
# and specify the fully qualified class name to the JavaScript interface
# class:
#-keepclassmembers class fqcn.of.javascript.interface.for.webview {
# public *;
#}

# Uncomment this to preserve the line number information for
# debugging stack traces.
#-keepattributes SourceFile,LineNumberTable

# If you keep the line number information, uncomment this to
# hide the original source file name.
#-renamesourcefileattribute SourceFile

-keepattributes *Annotation*, InnerClasses
-dontnote kotlinx.serialization.SerializationKt
-keep,includedescriptorclasses class com.yourcompany.yourpackage.**$$serializer { *; } # <-- change package name to your app's
-keepclassmembers class com.yourcompany.yourpackage.** { # <-- change package name to your app's
*** Companion;
}
-keepclasseswithmembers class com.yourcompany.yourpackage.** { # <-- change package name to your app's
kotlinx.serialization.KSerializer serializer(...);
}
Original file line number Diff line number Diff line change
@@ -1,31 +1,91 @@
package com.joaquimley.transporteta.sharedpreferences

import android.content.SharedPreferences
import com.joaquimley.transporteta.data.model.TransportEntity
import com.joaquimley.transporteta.data.source.FrameworkLocalStorage
import com.joaquimley.transporteta.sharedpreferences.mapper.SharedPrefTransportMapper
import com.joaquimley.transporteta.sharedpreferences.model.SharedPrefTransport
import io.reactivex.Completable
import io.reactivex.Single
import io.reactivex.subjects.PublishSubject
import javax.inject.Inject
import javax.inject.Singleton

@Singleton
class FrameworkLocalStorageImpl @Inject constructor(private val sharedPreferences: SharedPreferences,
private val mapper: SharedPrefTransportMapper) : FrameworkLocalStorage {

private val sharedPreferencesObservable: PublishSubject<List<TransportEntity>> = PublishSubject.create()

init {
loadAll()
observeSharedPreferencesChanges()
}

class FrameworkLocalStorageImpl: FrameworkLocalStorage {
override fun saveTransport(transportEntity: TransportEntity): Completable {
return Completable.complete()
return Completable.fromAction {
saveToSharedPrefs(mapper.toSharedPref(transportEntity))
}
}

override fun deleteTransport(transportEntityId: String): Completable {
return Completable.complete()
}

override fun getTransport(transportEntityId: String): Single<TransportEntity> {
return Single.just(TransportEntity("hi", "mock",2, "el", true,"bus"))
return Single.just(TransportEntity("hi", "mock", 2, "el", true, "bus"))
}

override fun getAll(): Single<List<TransportEntity>> {
val list = mutableListOf<TransportEntity>()
list.add(TransportEntity("hi", "mock",2, "latestEta 12324", true,"bus"))
list.add(TransportEntity("there", "mock",23, "latestEta 123", true,"bus"))
list.add(TransportEntity("hi", "mock", 2, "latestEta 12324", true, "bus"))
list.add(TransportEntity("there", "mock", 23, "latestEta 123", true, "bus"))
list.add(TransportEntity("world", "mock", 25, "latestEta 12454", true, "bus"))
list.add(TransportEntity("sup", "mock", 29, "latestEta 675", true, "bus"))
return Single.just(list)
}

override fun clearAll(): Completable {
return Completable.complete()
return Completable.fromAction {

}
}

private fun observeSharedPreferencesChanges() {
sharedPreferences.registerOnSharedPreferenceChangeListener { _, key ->
if (key != SHARED_PREFERENCES_LAST_UPDATED) {
loadAll()
}
}
}

private fun loadAll() {
val data = mutableListOf<TransportEntity>()
getFromSharedPrefs(Slot.ONE)?.let { data.add(mapper.toEntity(it)) }
getFromSharedPrefs(Slot.TWO)?.let { data.add(mapper.toEntity(it)) }
getFromSharedPrefs(Slot.THREE)?.let { data.add(mapper.toEntity(it)) }
sharedPreferencesObservable.onNext(data)
}

private fun saveToSharedPrefs(sharedPrefTransport: SharedPrefTransport) {
sharedPreferences.edit()
.putString(Slot.ONE.name, mapper.toCacheString(sharedPrefTransport))
.apply()
}

private fun getFromSharedPrefs(slot: Slot): SharedPrefTransport? {
sharedPreferences.getString(slot.name, null)?.let {
return mapper.fromCacheString(it)
} ?: return null
}

companion object {
private const val SHARED_PREFERENCES_LAST_UPDATED = "sharedpreferences.last_updated"
}

enum class Slot(name: String) {
ONE("transport_eta_fav_1"),
TWO("transport_eta_fav_2"),
THREE("transport_eta_fav_3"),
}
}
}

This file was deleted.

Original file line number Diff line number Diff line change
@@ -0,0 +1,32 @@
package com.joaquimley.transporteta.sharedpreferences.mapper

import com.joaquimley.transporteta.data.model.TransportEntity
import com.joaquimley.transporteta.sharedpreferences.model.SharedPrefTransport
import kotlinx.serialization.json.JSON

class SharedPrefTransportMapper {

fun toCacheString(from: SharedPrefTransport): String {
return JSON.stringify(from)
}

fun fromCacheString(from: String): SharedPrefTransport {
return JSON.parse(from)
}

fun toSharedPref(from: List<TransportEntity>): List<SharedPrefTransport> {
return from.map { toSharedPref(it) }
}

fun toSharedPref(from: TransportEntity): SharedPrefTransport {
return SharedPrefTransport(from.id, from.name, from.code, from.latestEta, from.isFavorite, from.type, 1312, "")
}

fun toEntity(from: List<SharedPrefTransport>): List<TransportEntity> {
return from.map { toEntity(it) }
}

fun toEntity(from: SharedPrefTransport): TransportEntity {
return TransportEntity(from.id, from.name, from.code, from.latestEta, from.isFavorite, from.type)
}
}
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
package com.joaquimley.transporteta.sharedpreferences.model

class SharedPrefTransport {

// TODO
}
@kotlinx.serialization.Serializable
data class SharedPrefTransport(val id: String, val name: String, val code: Int, val latestEta: String,
val isFavorite: Boolean = false, val type: String, val lastUpdated: Long,
val slot: String)

This file was deleted.

Loading

0 comments on commit 2d10258

Please sign in to comment.