Improved backup/restore w/o Crypto class

This commit is contained in:
Juha Heinanen
2022-02-09 12:52:09 +02:00
parent 52f693f49c
commit d975ab522a
2 changed files with 31 additions and 36 deletions

View File

@ -35,12 +35,11 @@ import com.google.android.material.snackbar.Snackbar
import com.tutpro.baresip.Utils.showSnackBar
import com.tutpro.baresip.databinding.ActivityMainBinding
import java.io.File
import java.io.FileInputStream
import java.io.FileOutputStream
import java.net.URLDecoder
import kotlin.collections.ArrayList
import kotlin.system.exitProcess
import android.content.IntentFilter
import androidx.core.net.toUri
class MainActivity : AppCompatActivity() {
@ -88,10 +87,8 @@ class MainActivity : AppCompatActivity() {
private lateinit var contactsRequest: ActivityResultLauncher<Intent>
private lateinit var callsRequest: ActivityResultLauncher<Intent>
private var downloadsInputStream: FileInputStream? = null
private var downloadsOutputStream: FileOutputStream? = null
private var downloadsInputFile = "baresip.bs"
private var downloadsOutputFile = "baresip.bs"
private var downloadsInputUri: Uri? = null
private var downloadsOutputUri: Uri? = null
private lateinit var baresipService: Intent
@ -543,24 +540,18 @@ class MainActivity : AppCompatActivity() {
backupRequest = registerForActivityResult(ActivityResultContracts.StartActivityForResult()) {
if (it.resultCode == Activity.RESULT_OK)
it.data?.data?.also { uri ->
downloadsOutputStream = applicationContext.contentResolver.openOutputStream(uri)
as FileOutputStream
if (downloadsOutputStream != null) {
downloadsOutputFile = Utils.fileNameOfUri(applicationContext, uri)
downloadsOutputUri = uri
if (downloadsOutputUri != null)
askPassword(getString(R.string.encrypt_password))
}
}
}
restoreRequest = registerForActivityResult(ActivityResultContracts.StartActivityForResult()) {
if (it.resultCode == Activity.RESULT_OK)
it.data?.data?.also { uri ->
downloadsInputStream = applicationContext.contentResolver.openInputStream(uri)
as FileInputStream
if (downloadsInputStream != null) {
downloadsInputFile = Utils.fileNameOfUri(applicationContext, uri)
downloadsInputUri = uri
if (downloadsInputUri != null)
askPassword(getString(R.string.decrypt_password))
}
}
}
@ -1266,7 +1257,7 @@ class MainActivity : AppCompatActivity() {
) == PackageManager.PERMISSION_GRANTED -> {
Log.d(TAG, "Write External Storage permission granted")
val path = Utils.downloadsPath("baresip.bs")
downloadsOutputStream = FileOutputStream(File(path))
downloadsOutputUri = File(path).toUri()
askPassword(getString(R.string.encrypt_password))
}
ActivityCompat.shouldShowRequestPermissionRationale(
@ -1289,14 +1280,15 @@ class MainActivity : AppCompatActivity() {
R.id.restore -> {
when {
Build.VERSION.SDK_INT >= 29 -> pickupFileFromDownloads("restore")
Build.VERSION.SDK_INT >= 29 ->
pickupFileFromDownloads("restore")
ContextCompat.checkSelfPermission(
this,
Manifest.permission.READ_EXTERNAL_STORAGE
) == PackageManager.PERMISSION_GRANTED -> {
Log.d(TAG, "Read External Storage permission granted")
val path = Utils.downloadsPath("baresip.bs")
downloadsInputStream = FileInputStream(File(path))
downloadsInputUri = File(path).toUri()
askPassword(getString(R.string.decrypt_password))
}
ActivityCompat.shouldShowRequestPermissionRationale(
@ -1552,7 +1544,7 @@ class MainActivity : AppCompatActivity() {
Log.w(TAG, "Failed to write zip file '$zipFile'")
Utils.alertView(this, getString(R.string.error),
String.format(getString(R.string.backup_failed),
downloadsOutputFile))
Utils.fileNameOfUri(applicationContext, downloadsOutputUri!!)))
return
}
val content = Utils.getFileContents(zipFilePath)
@ -1560,43 +1552,43 @@ class MainActivity : AppCompatActivity() {
Log.w(TAG, "Failed to read zip file '$zipFile'")
Utils.alertView(this, getString(R.string.error),
String.format(getString(R.string.backup_failed),
downloadsOutputFile))
Utils.fileNameOfUri(applicationContext, downloadsOutputUri!!)))
return
}
if (!Utils.encryptToStream(downloadsOutputStream, content, password)) {
if (!Utils.encryptToUri(applicationContext, downloadsOutputUri!!, content, password)) {
Utils.alertView(this, getString(R.string.error),
String.format(getString(R.string.backup_failed),
downloadsOutputFile))
Utils.fileNameOfUri(applicationContext, downloadsOutputUri!!)))
return
}
Utils.alertView(this, getString(R.string.info),
String.format(getString(R.string.backed_up),
downloadsOutputFile))
Utils.fileNameOfUri(applicationContext, downloadsOutputUri!!)))
Utils.deleteFile(File(zipFilePath))
}
private fun restore(password: String) {
val zipFile = getString(R.string.app_name) + ".zip"
val zipFilePath = BaresipService.filesPath + "/$zipFile"
val zipData = Utils.decryptFromStream(downloadsInputStream, password)
val zipData = Utils.decryptFromUri(applicationContext, downloadsInputUri!!, password)
if (zipData == null) {
Utils.alertView(this, getString(R.string.error),
String.format(getString(R.string.restore_failed),
downloadsInputFile))
Utils.fileNameOfUri(applicationContext, downloadsInputUri!!)))
return
}
if (!Utils.putFileContents(zipFilePath, zipData)) {
Log.w(TAG, "Failed to write zip file '$zipFile'")
Utils.alertView(this, getString(R.string.error),
String.format(getString(R.string.restore_failed),
downloadsInputFile))
Utils.fileNameOfUri(applicationContext, downloadsInputUri!!)))
return
}
if (!Utils.unZip(zipFilePath)) {
Log.w(TAG, "Failed to unzip file '$zipFile'")
Utils.alertView(this, getString(R.string.error),
String.format(getString(R.string.restore_failed),
downloadsInputFile))
Utils.fileNameOfUri(applicationContext, downloadsInputUri!!)))
return
}
Utils.deleteFile(File(zipFilePath))

View File

@ -629,38 +629,41 @@ object Utils {
return plainData
}
fun encryptToStream(stream: FileOutputStream?, content: ByteArray, password: String): Boolean {
fun encryptToUri(ctx: Context, uri: Uri, content: ByteArray, password: String): Boolean {
val obj = encrypt(content, password.toCharArray())
val stream = ctx.contentResolver.openOutputStream(uri) as FileOutputStream
try {
ObjectOutputStream(stream).use {
it.writeObject(obj)
}
} catch (e: Exception) {
Log.w(TAG, "encryptToStream failed: $e")
Log.w(TAG, "encryptToUri failed: $e")
return false
}
return true
}
fun decryptFromStream(stream: FileInputStream?, password: String): ByteArray? {
fun decryptFromUri(ctx: Context, uri: Uri, password: String): ByteArray? {
var plainData: ByteArray? = null
if (stream == null)
return null
var stream = ctx.contentResolver.openInputStream(uri) as FileInputStream
try {
ObjectInputStream(stream).use {
val content = it.readObject() as ByteArray
plainData = decrypt(content, password.toCharArray())
}
stream.close()
} catch (e: Exception) {
Log.w(TAG, "decryptFromStream as ByteArray failed: $e")
Log.w(TAG, "decryptFromUri as ByteArray failed: $e")
stream.close()
try {
stream.close()
stream = ctx.contentResolver.openInputStream(uri) as FileInputStream
ObjectInputStream(stream).use {
val obj = it.readObject() as Crypto
plainData = decryptOld(obj, password.toCharArray())
}
stream.close()
} catch (e: Exception) {
Log.w(TAG, "decryptFromStream as Crypto failed: $e")
Log.w(TAG, "decryptFromUri as Crypto failed: $e")
}
}
return plainData