summaryrefslogtreecommitdiff
path: root/cashier
diff options
context:
space:
mode:
authorTorsten Grote <t@grobox.de>2020-04-22 15:10:08 -0300
committerTorsten Grote <t@grobox.de>2020-04-22 15:10:08 -0300
commitd57645954dda2d478fe09dd0135183e1b3526db0 (patch)
tree3149d52c2b020844fe9031ee8b5a69cdece6e0a3 /cashier
parentf920fa7fa12db5d6fd40844ffb8402426d0a2b07 (diff)
downloadtaler-android-d57645954dda2d478fe09dd0135183e1b3526db0.tar.gz
taler-android-d57645954dda2d478fe09dd0135183e1b3526db0.tar.bz2
taler-android-d57645954dda2d478fe09dd0135183e1b3526db0.zip
[cashier] expose internal error messages to UI
Diffstat (limited to 'cashier')
-rw-r--r--cashier/src/main/java/net/taler/cashier/BalanceFragment.kt32
-rw-r--r--cashier/src/main/java/net/taler/cashier/ConfigFragment.kt22
-rw-r--r--cashier/src/main/java/net/taler/cashier/HttpHelper.kt27
-rw-r--r--cashier/src/main/java/net/taler/cashier/MainViewModel.kt16
-rw-r--r--cashier/src/main/java/net/taler/cashier/withdraw/WithdrawManager.kt2
-rw-r--r--cashier/src/main/res/values/strings.xml6
6 files changed, 68 insertions, 37 deletions
diff --git a/cashier/src/main/java/net/taler/cashier/BalanceFragment.kt b/cashier/src/main/java/net/taler/cashier/BalanceFragment.kt
index c4802ee..246cba0 100644
--- a/cashier/src/main/java/net/taler/cashier/BalanceFragment.kt
+++ b/cashier/src/main/java/net/taler/cashier/BalanceFragment.kt
@@ -35,11 +35,12 @@ import net.taler.cashier.withdraw.LastTransaction
import net.taler.cashier.withdraw.WithdrawStatus
import net.taler.common.Amount
import net.taler.common.SignedAmount
+import net.taler.common.exhaustive
import net.taler.common.fadeIn
import net.taler.common.fadeOut
sealed class BalanceResult {
- object Error : BalanceResult()
+ class Error(val msg: String) : BalanceResult()
object Offline : BalanceResult()
class Success(val amount: SignedAmount) : BalanceResult()
}
@@ -62,10 +63,7 @@ class BalanceFragment : Fragment() {
onLastTransaction(lastTransaction)
})
viewModel.balance.observe(viewLifecycleOwner, Observer { result ->
- when (result) {
- is BalanceResult.Success -> onBalanceUpdated(result.amount)
- else -> onBalanceUpdated(null, result is BalanceResult.Offline)
- }
+ onBalanceUpdated(result)
})
button5.setOnClickListener { onAmountButtonPressed(5) }
button10.setOnClickListener { onAmountButtonPressed(10) }
@@ -121,20 +119,26 @@ class BalanceFragment : Fragment() {
else -> super.onOptionsItemSelected(item)
}
- private fun onBalanceUpdated(amount: SignedAmount?, isOffline: Boolean = false) {
+ private fun onBalanceUpdated(result: BalanceResult) {
val uiList = listOf(
introView,
button5, button10, button20, button50,
amountView, currencyView, confirmWithdrawalButton
)
- if (amount == null) {
- balanceView.text =
- getString(if (isOffline) R.string.balance_offline else R.string.balance_error)
- uiList.forEach { it.fadeOut() }
- } else {
- balanceView.text = amount.toString()
- uiList.forEach { it.fadeIn() }
- }
+ when (result) {
+ is BalanceResult.Success -> {
+ balanceView.text = result.amount.toString()
+ uiList.forEach { it.fadeIn() }
+ }
+ is BalanceResult.Error -> {
+ balanceView.text = getString(R.string.balance_error, result.msg)
+ uiList.forEach { it.fadeOut() }
+ }
+ BalanceResult.Offline -> {
+ balanceView.text = getString(R.string.balance_offline)
+ uiList.forEach { it.fadeOut() }
+ }
+ }.exhaustive
progressBar.fadeOut()
}
diff --git a/cashier/src/main/java/net/taler/cashier/ConfigFragment.kt b/cashier/src/main/java/net/taler/cashier/ConfigFragment.kt
index ccbb1a6..f435883 100644
--- a/cashier/src/main/java/net/taler/cashier/ConfigFragment.kt
+++ b/cashier/src/main/java/net/taler/cashier/ConfigFragment.kt
@@ -34,6 +34,7 @@ import androidx.navigation.fragment.findNavController
import com.google.android.material.snackbar.BaseTransientBottomBar.LENGTH_LONG
import com.google.android.material.snackbar.Snackbar
import kotlinx.android.synthetic.main.fragment_config.*
+import net.taler.common.exhaustive
private const val URL_BANK_TEST = "https://bank.test.taler.net"
private const val URL_BANK_TEST_REGISTER = "$URL_BANK_TEST/accounts/register"
@@ -125,13 +126,20 @@ class ConfigFragment : Fragment() {
private val onConfigResult = Observer<ConfigResult> { result ->
if (result == null) return@Observer
- if (result.success) {
- val action = ConfigFragmentDirections.actionConfigFragmentToBalanceFragment()
- findNavController().navigate(action)
- } else {
- val res = if (result.authError) R.string.config_error_auth else R.string.config_error
- Snackbar.make(view!!, res, LENGTH_LONG).show()
- }
+ when (result) {
+ is ConfigResult.Success -> {
+ val action = ConfigFragmentDirections.actionConfigFragmentToBalanceFragment()
+ findNavController().navigate(action)
+ }
+ is ConfigResult.Error -> {
+ if (result.authError) {
+ Snackbar.make(view!!, R.string.config_error_auth, LENGTH_LONG).show()
+ } else {
+ val str = getString(R.string.config_error, result.msg)
+ Snackbar.make(view!!, str, LENGTH_LONG).show()
+ }
+ }
+ }.exhaustive
saveButton.visibility = VISIBLE
progressBar.visibility = INVISIBLE
viewModel.configResult.removeObservers(viewLifecycleOwner)
diff --git a/cashier/src/main/java/net/taler/cashier/HttpHelper.kt b/cashier/src/main/java/net/taler/cashier/HttpHelper.kt
index 63eaddf..49a43d1 100644
--- a/cashier/src/main/java/net/taler/cashier/HttpHelper.kt
+++ b/cashier/src/main/java/net/taler/cashier/HttpHelper.kt
@@ -23,6 +23,8 @@ import okhttp3.MediaType
import okhttp3.OkHttpClient
import okhttp3.Request
import okhttp3.RequestBody
+import okhttp3.Response
+import org.json.JSONException
import org.json.JSONObject
object HttpHelper {
@@ -43,14 +45,14 @@ object HttpHelper {
.execute()
} catch (e: Exception) {
Log.e(TAG, "Error retrieving $url", e)
- return HttpJsonResult.Error(500)
+ return HttpJsonResult.Error(0)
}
return if (response.code() == 200 && response.body() != null) {
val jsonObject = JSONObject(response.body()!!.string())
HttpJsonResult.Success(jsonObject)
} else {
Log.e(TAG, "Received status ${response.code()} from $url expected 200")
- HttpJsonResult.Error(response.code())
+ HttpJsonResult.Error(response.code(), getErrorBody(response))
}
}
@@ -69,14 +71,14 @@ object HttpHelper {
.execute()
} catch (e: Exception) {
Log.e(TAG, "Error retrieving $url", e)
- return HttpJsonResult.Error(500)
+ return HttpJsonResult.Error(0)
}
return if (response.code() == 200 && response.body() != null) {
val jsonObject = JSONObject(response.body()!!.string())
HttpJsonResult.Success(jsonObject)
} else {
Log.e(TAG, "Received status ${response.code()} from $url expected 200")
- HttpJsonResult.Error(response.code())
+ HttpJsonResult.Error(response.code(), getErrorBody(response))
}
}
@@ -94,9 +96,24 @@ object HttpHelper {
.build()
}.build()
+ private fun getErrorBody(response: Response): String? {
+ val body = response.body()?.string() ?: return null
+ Log.e(TAG, "Response body: $body")
+ return try {
+ val json = JSONObject(body)
+ "${json.optString("ec")} ${json.optString("error")}"
+ } catch (e: JSONException) {
+ null
+ }
+ }
+
}
sealed class HttpJsonResult {
- class Error(val statusCode: Int) : HttpJsonResult()
+ class Error(val statusCode: Int, private val errorMsg: String? = null) : HttpJsonResult() {
+ val msg: String
+ get() = errorMsg?.let { "\n\n$statusCode $it" } ?: ": $statusCode"
+ }
+
class Success(val json: JSONObject) : HttpJsonResult()
}
diff --git a/cashier/src/main/java/net/taler/cashier/MainViewModel.kt b/cashier/src/main/java/net/taler/cashier/MainViewModel.kt
index 2b2d5f7..3587e95 100644
--- a/cashier/src/main/java/net/taler/cashier/MainViewModel.kt
+++ b/cashier/src/main/java/net/taler/cashier/MainViewModel.kt
@@ -97,14 +97,13 @@ class MainViewModel(private val app: Application) : AndroidViewModel(app) {
prefs.edit().putString(PREF_KEY_CURRENCY, amount.amount.currency).apply()
// save config
saveConfig(config)
- ConfigResult(true)
+ ConfigResult.Success
} catch (e: AmountParserException) {
- ConfigResult(false)
+ ConfigResult.Error(false, "Invalid Amount: $balance")
}
}
is HttpJsonResult.Error -> {
- val authError = response.statusCode == 401
- ConfigResult(false, authError)
+ ConfigResult.Error(response.statusCode == 401, response.msg)
}
}
mConfigResult.postValue(result)
@@ -132,11 +131,11 @@ class MainViewModel(private val app: Application) : AndroidViewModel(app) {
try {
BalanceResult.Success(SignedAmount.fromJSONString(balance))
} catch (e: AmountParserException) {
- BalanceResult.Error
+ BalanceResult.Error("invalid amount: $balance")
}
}
is HttpJsonResult.Error -> {
- if (app.isOnline()) BalanceResult.Error
+ if (app.isOnline()) BalanceResult.Error(response.msg)
else BalanceResult.Offline
}
}
@@ -155,4 +154,7 @@ data class Config(
val password: String
)
-class ConfigResult(val success: Boolean, val authError: Boolean = false)
+sealed class ConfigResult {
+ class Error(val authError: Boolean, val msg: String) : ConfigResult()
+ object Success : ConfigResult()
+}
diff --git a/cashier/src/main/java/net/taler/cashier/withdraw/WithdrawManager.kt b/cashier/src/main/java/net/taler/cashier/withdraw/WithdrawManager.kt
index 317d1bf..edefa5a 100644
--- a/cashier/src/main/java/net/taler/cashier/withdraw/WithdrawManager.kt
+++ b/cashier/src/main/java/net/taler/cashier/withdraw/WithdrawManager.kt
@@ -102,7 +102,7 @@ class WithdrawManager(
timer.start()
}
is Error -> {
- val errorStr = app.getString(R.string.withdraw_error_fetch)
+ val errorStr = app.getString(R.string.withdraw_error_fetch, result.msg)
mWithdrawResult.postValue(WithdrawResult.Error(errorStr))
}
}
diff --git a/cashier/src/main/res/values/strings.xml b/cashier/src/main/res/values/strings.xml
index 98f686c..43e3573 100644
--- a/cashier/src/main/res/values/strings.xml
+++ b/cashier/src/main/res/values/strings.xml
@@ -7,12 +7,12 @@
<string name="config_button_save">Save</string>
<string name="config_bank_url_error">The address in invalid.</string>
<string name="config_username_error">Please enter your username</string>
- <string name="config_error">Error retrieving configuration</string>
+ <string name="config_error">Error retrieving configuration%s</string>
<string name="config_error_auth">Invalid username or password</string>
<string name="config_demo_hint" tools:ignore="StringFormatInvalid">For testing, you can <![CDATA[<a href="%s">create a test account at the demo bank</a>]]>.</string>
<string name="balance_current_label">Current balance</string>
- <string name="balance_error">ERROR</string>
+ <string name="balance_error">ERROR%s</string>
<string name="balance_offline">Offline. Please connect to the Internet</string>
<string name="action_reconfigure">Reconfigure</string>
<string name="action_lock">Lock</string>
@@ -21,7 +21,7 @@
<string name="withdraw_into">How much e-cash should be withdrawn?</string>
<string name="withdraw_error_zero">Enter positive amount</string>
<string name="withdraw_error_insufficient_balance">Insufficient balance</string>
- <string name="withdraw_error_fetch">Error communicating with bank</string>
+ <string name="withdraw_error_fetch">Error communicating with bank%s</string>
<string name="withdraw_button_confirm">Withdraw</string>
<string name="transaction_intro">Scan code\nwith the Taler wallet app\nto get</string>