Initiated CSV auto custom field mapping

csv
Laurent 6 years ago
parent fa9b6317fd
commit 36f52b6681
  1. 41
      app/src/main/java/net/pokeranalytics/android/util/csv/CSVDescriptor.kt
  2. 14
      app/src/main/java/net/pokeranalytics/android/util/csv/CSVField.kt
  3. 9
      app/src/main/java/net/pokeranalytics/android/util/csv/CSVImporter.kt
  4. 11
      app/src/main/java/net/pokeranalytics/android/util/csv/ProductCSVDescriptors.kt
  5. 22
      app/src/main/java/net/pokeranalytics/android/util/csv/SessionField.kt

@ -4,6 +4,7 @@ import io.realm.Realm
import io.realm.kotlin.deleteFromRealm import io.realm.kotlin.deleteFromRealm
import net.pokeranalytics.android.model.interfaces.Identifiable import net.pokeranalytics.android.model.interfaces.Identifiable
import net.pokeranalytics.android.model.interfaces.ObjectIdentifier import net.pokeranalytics.android.model.interfaces.ObjectIdentifier
import net.pokeranalytics.android.model.realm.CustomField
import net.pokeranalytics.android.model.realm.Session import net.pokeranalytics.android.model.realm.Session
import net.pokeranalytics.android.util.extensions.findById import net.pokeranalytics.android.util.extensions.findById
import org.apache.commons.csv.CSVRecord import org.apache.commons.csv.CSVRecord
@ -26,7 +27,7 @@ abstract class DataCSVDescriptor<T : Identifiable>(source: DataSource, vararg el
/** /**
* List of Realm object identificators * List of Realm object identificators
*/ */
val realmModelIds = mutableListOf<ObjectIdentifier>() private val realmModelIds = mutableListOf<ObjectIdentifier>()
abstract fun parseData(realm: Realm, record: CSVRecord): T? abstract fun parseData(realm: Realm, record: CSVRecord): T?
@ -83,27 +84,17 @@ abstract class CSVDescriptor(var source: DataSource, vararg elements: CSVField)
/** /**
* The CSVField list describing the CSV header format * The CSVField list describing the CSV header format
*/ */
protected var fields: List<CSVField> = listOf() protected var fields: MutableList<CSVField> = mutableListOf()
/** /**
* The mapping of CSVField with their index in the CSV file * The mapping of CSVField with their index in the CSV file
*/ */
protected var fieldMapping: MutableMap<CSVField, Int> = mutableMapOf() protected var fieldMapping: MutableMap<CSVField, Int> = mutableMapOf()
init { init {
if (elements.size > 0) { if (elements.isNotEmpty()) {
this.fields = elements.toList() this.fields = elements.toMutableList()
}
} }
companion object {
/**
* The list of all managed CSVDescriptors
*/
val all: List<CSVDescriptor> =
listOf(ProductCSVDescriptors.pokerIncomeCash,
ProductCSVDescriptors.pokerBankrollTracker,
ProductCSVDescriptors.runGoodCashGames,
ProductCSVDescriptors.runGoodTournaments)
} }
/** /**
@ -140,4 +131,24 @@ abstract class CSVDescriptor(var source: DataSource, vararg elements: CSVField)
return count >= mandatoryfields.size return count >= mandatoryfields.size
} }
fun mapCustomField(record: CSVRecord, realm: Realm) {
val customFields = realm.where(CustomField::class.java).findAll()
val headers = record.toSet()
headers.forEach { header ->
val customField = customFields.firstOrNull { it.name == header }
customField?.let {
if (it.isListType) {
} else {
val f = MappedCustomCVSField.Number(header, null, "", it)
fields.add(f)
}
}
}
}
} }

@ -1,5 +1,7 @@
package net.pokeranalytics.android.util.csv package net.pokeranalytics.android.util.csv
import net.pokeranalytics.android.model.realm.CustomField
import net.pokeranalytics.android.model.realm.CustomFieldEntry
import timber.log.Timber import timber.log.Timber
import java.text.DateFormat import java.text.DateFormat
import java.text.NumberFormat import java.text.NumberFormat
@ -82,6 +84,18 @@ interface BlindCSVField : TypedCSVField<Pair<Double, Double>> {
} }
interface CustomEntryCSVField : TypedCSVField<CustomFieldEntry>, CustomCSVField {
}
interface CustomNumberCSVField : NumberCSVField, CustomCSVField {
}
interface CustomCSVField {
var customField: CustomField
}
interface TypedCSVField<T> : CSVField { interface TypedCSVField<T> : CSVField {
fun parse(value: String) : T? fun parse(value: String) : T?
var callback: ((String) -> T?)? var callback: ((String) -> T?)?

@ -36,10 +36,12 @@ open class CSVImporter(istream: InputStream) {
* Number of commits required to commit a Realm transaction * Number of commits required to commit a Realm transaction
*/ */
private val COMMIT_FREQUENCY = 100 private val COMMIT_FREQUENCY = 100
/** /**
* The number of column indicating a valid record * The number of column indicating a valid record
*/ */
private val VALID_RECORD_COLUMNS = 4 private val VALID_RECORD_COLUMNS = 4
/** /**
* The number of valid record to test for descriptor before throwing a File Format Exception * The number of valid record to test for descriptor before throwing a File Format Exception
*/ */
@ -111,7 +113,7 @@ open class CSVImporter(istream: InputStream) {
this.notifyDelegate() this.notifyDelegate()
if (this.currentDescriptor == null) { // find descriptor if (this.currentDescriptor == null) { // find descriptor
this.currentDescriptor = this.findDescriptor(record) this.currentDescriptor = this.findDescriptor(record, realm)
if (this.currentDescriptor == null) { if (this.currentDescriptor == null) {
@ -174,10 +176,11 @@ open class CSVImporter(istream: InputStream) {
/** /**
* Search for a descriptor in the list of managed formats * Search for a descriptor in the list of managed formats
*/ */
private fun findDescriptor(record: CSVRecord): CSVDescriptor? { private fun findDescriptor(record: CSVRecord, realm: Realm): CSVDescriptor? {
CSVDescriptor.all.forEach { descriptor -> ProductCSVDescriptors.all.forEach { descriptor ->
if (descriptor.matches(record)) { if (descriptor.matches(record)) {
descriptor.mapCustomField(record, realm)
this.currentDescriptor = descriptor this.currentDescriptor = descriptor
Timber.d("Identified source: ${descriptor.source}") Timber.d("Identified source: ${descriptor.source}")
return descriptor return descriptor

@ -4,6 +4,17 @@ class ProductCSVDescriptors {
companion object { companion object {
/**
* The list of all managed CSVDescriptors
*/
val all: List<CSVDescriptor> =
listOf(
ProductCSVDescriptors.pokerIncomeCash,
ProductCSVDescriptors.pokerBankrollTracker,
ProductCSVDescriptors.runGoodCashGames,
ProductCSVDescriptors.runGoodTournaments
)
val pokerIncomeCash: CSVDescriptor = SessionCSVDescriptor( val pokerIncomeCash: CSVDescriptor = SessionCSVDescriptor(
DataSource.POKER_INCOME, DataSource.POKER_INCOME,
false, false,

@ -1,7 +1,29 @@
package net.pokeranalytics.android.util.csv package net.pokeranalytics.android.util.csv
import net.pokeranalytics.android.model.realm.CustomField
import net.pokeranalytics.android.model.realm.CustomFieldEntry
import java.util.* import java.util.*
sealed class MappedCustomCVSField {
data class Number(
override var header: String,
override var callback: ((String) -> Double?)? = null,
override val numberFormat: String?,
override var customField: CustomField) : CustomNumberCSVField
data class List(
override var header: String,
override var callback: ((String) -> CustomFieldEntry?)? = null,
override var customField: CustomField) : CustomEntryCSVField {
override fun parse(value: String): CustomFieldEntry? {
TODO("not implemented") //To change body of created functions use File | Settings | File Templates.
}
}
}
sealed class TransactionField { sealed class TransactionField {
data class TransactionType( data class TransactionType(

Loading…
Cancel
Save