AutofillDecryptActivity: use runCatching to replace exception handling

Signed-off-by: Harsh Shandilya <me@msfjarvis.dev>
This commit is contained in:
Harsh Shandilya 2020-09-05 04:28:44 +05:30
parent 8ed6dad23c
commit 0bc60999c3
No known key found for this signature in database
GPG key ID: 366D7BBAD1031E80

View file

@ -18,6 +18,10 @@ import androidx.annotation.RequiresApi
import androidx.appcompat.app.AppCompatActivity import androidx.appcompat.app.AppCompatActivity
import com.github.ajalt.timberkt.d import com.github.ajalt.timberkt.d
import com.github.ajalt.timberkt.e import com.github.ajalt.timberkt.e
import com.github.michaelbull.result.getOrElse
import com.github.michaelbull.result.onFailure
import com.github.michaelbull.result.onSuccess
import com.github.michaelbull.result.runCatching
import com.zeapo.pwdstore.autofill.oreo.AutofillAction import com.zeapo.pwdstore.autofill.oreo.AutofillAction
import com.zeapo.pwdstore.autofill.oreo.AutofillPreferences import com.zeapo.pwdstore.autofill.oreo.AutofillPreferences
import com.zeapo.pwdstore.autofill.oreo.Credentials import com.zeapo.pwdstore.autofill.oreo.Credentials
@ -27,10 +31,8 @@ import com.zeapo.pwdstore.model.PasswordEntry
import com.zeapo.pwdstore.utils.OPENPGP_PROVIDER import com.zeapo.pwdstore.utils.OPENPGP_PROVIDER
import java.io.ByteArrayOutputStream import java.io.ByteArrayOutputStream
import java.io.File import java.io.File
import java.io.FileNotFoundException
import java.io.InputStream import java.io.InputStream
import java.io.OutputStream import java.io.OutputStream
import java.io.UnsupportedEncodingException
import kotlin.coroutines.Continuation import kotlin.coroutines.Continuation
import kotlin.coroutines.resume import kotlin.coroutines.resume
import kotlin.coroutines.resumeWithException import kotlin.coroutines.resumeWithException
@ -162,77 +164,80 @@ class AutofillDecryptActivity : AppCompatActivity(), CoroutineScope {
val command = resumeIntent ?: Intent().apply { val command = resumeIntent ?: Intent().apply {
action = OpenPgpApi.ACTION_DECRYPT_VERIFY action = OpenPgpApi.ACTION_DECRYPT_VERIFY
} }
val encryptedInput = try { runCatching {
file.inputStream() file.inputStream()
} catch (e: FileNotFoundException) { }.onFailure { e ->
e(e) { "File to decrypt not found" } e(e) { "File to decrypt not found" }
return null return null
} }.onSuccess { encryptedInput ->
val decryptedOutput = ByteArrayOutputStream() val decryptedOutput = ByteArrayOutputStream()
val result = try { runCatching {
executeOpenPgpApi(command, encryptedInput, decryptedOutput) executeOpenPgpApi(command, encryptedInput, decryptedOutput)
} catch (e: Exception) { }.onFailure { e ->
e(e) { "OpenPgpApi ACTION_DECRYPT_VERIFY failed" } e(e) { "OpenPgpApi ACTION_DECRYPT_VERIFY failed" }
return null return null
} }.onSuccess { result ->
return when (val resultCode = return when (val resultCode =
result?.getIntExtra(OpenPgpApi.RESULT_CODE, OpenPgpApi.RESULT_CODE_ERROR)) { result?.getIntExtra(OpenPgpApi.RESULT_CODE, OpenPgpApi.RESULT_CODE_ERROR)) {
OpenPgpApi.RESULT_CODE_SUCCESS -> { OpenPgpApi.RESULT_CODE_SUCCESS -> {
try { runCatching {
val entry = withContext(Dispatchers.IO) { val entry = withContext(Dispatchers.IO) {
@Suppress("BlockingMethodInNonBlockingContext") @Suppress("BlockingMethodInNonBlockingContext")
PasswordEntry(decryptedOutput) PasswordEntry(decryptedOutput)
} }
Credentials.fromStoreEntry(this, file, entry, directoryStructure) Credentials.fromStoreEntry(this, file, entry, directoryStructure)
} catch (e: UnsupportedEncodingException) { }.getOrElse { e ->
e(e) { "Failed to parse password entry" } e(e) { "Failed to parse password entry" }
null return null
}
}
OpenPgpApi.RESULT_CODE_USER_INTERACTION_REQUIRED -> {
val pendingIntent: PendingIntent =
result.getParcelableExtra(OpenPgpApi.RESULT_INTENT)!!
try {
val intentToResume = withContext(Dispatchers.Main) {
suspendCoroutine<Intent> { cont ->
continueAfterUserInteraction = cont
registerForActivityResult(StartIntentSenderForResult()) { result ->
if (continueAfterUserInteraction != null) {
val data = result.data
if (result.resultCode == RESULT_OK && data != null) {
continueAfterUserInteraction?.resume(data)
} else {
continueAfterUserInteraction?.resumeWithException(Exception("OpenPgpApi ACTION_DECRYPT_VERIFY failed to continue after user interaction"))
}
continueAfterUserInteraction = null
}
}.launch(IntentSenderRequest.Builder(pendingIntent.intentSender).build())
} }
} }
decryptCredential(file, intentToResume) OpenPgpApi.RESULT_CODE_USER_INTERACTION_REQUIRED -> {
} catch (e: Exception) { val pendingIntent: PendingIntent =
e(e) { "OpenPgpApi ACTION_DECRYPT_VERIFY failed with user interaction" } result.getParcelableExtra(OpenPgpApi.RESULT_INTENT)!!
null runCatching {
} val intentToResume = withContext(Dispatchers.Main) {
} suspendCoroutine<Intent> { cont ->
OpenPgpApi.RESULT_CODE_ERROR -> { continueAfterUserInteraction = cont
val error = result.getParcelableExtra<OpenPgpError>(OpenPgpApi.RESULT_ERROR) registerForActivityResult(StartIntentSenderForResult()) { result ->
if (error != null) { if (continueAfterUserInteraction != null) {
withContext(Dispatchers.Main) { val data = result.data
Toast.makeText( if (result.resultCode == RESULT_OK && data != null) {
applicationContext, continueAfterUserInteraction?.resume(data)
"Error from OpenKeyChain: ${error.message}", } else {
Toast.LENGTH_LONG continueAfterUserInteraction?.resumeWithException(Exception("OpenPgpApi ACTION_DECRYPT_VERIFY failed to continue after user interaction"))
).show() }
continueAfterUserInteraction = null
}
}.launch(IntentSenderRequest.Builder(pendingIntent.intentSender).build())
}
}
decryptCredential(file, intentToResume)
}.getOrElse { e ->
e(e) { "OpenPgpApi ACTION_DECRYPT_VERIFY failed with user interaction" }
return null
}
}
OpenPgpApi.RESULT_CODE_ERROR -> {
val error = result.getParcelableExtra<OpenPgpError>(OpenPgpApi.RESULT_ERROR)
if (error != null) {
withContext(Dispatchers.Main) {
Toast.makeText(
applicationContext,
"Error from OpenKeyChain: ${error.message}",
Toast.LENGTH_LONG
).show()
}
e { "OpenPgpApi ACTION_DECRYPT_VERIFY failed (${error.errorId}): ${error.message}" }
}
null
}
else -> {
e { "Unrecognized OpenPgpApi result: $resultCode" }
null
} }
e { "OpenPgpApi ACTION_DECRYPT_VERIFY failed (${error.errorId}): ${error.message}" }
} }
null
}
else -> {
e { "Unrecognized OpenPgpApi result: $resultCode" }
null
} }
} }
return null
} }
} }