From 9d8846e105904b31478ed19d3a34c0d62708abcf Mon Sep 17 00:00:00 2001
From: pacien
Date: Tue, 7 Aug 2018 01:08:22 +0200
Subject: Revert "Rename source directory"
This reverts commit dbba24e
---
.../org/pacien/tincapp/activities/BaseActivity.kt | 114 ----------
.../pacien/tincapp/activities/ConfigureActivity.kt | 145 -------------
.../org/pacien/tincapp/activities/StartActivity.kt | 201 ------------------
.../pacien/tincapp/activities/StatusActivity.kt | 196 -----------------
.../pacien/tincapp/activities/ViewLogActivity.kt | 164 --------------
.../kotlin/org/pacien/tincapp/commands/Command.kt | 46 ----
.../kotlin/org/pacien/tincapp/commands/Executor.kt | 85 --------
.../kotlin/org/pacien/tincapp/commands/Tinc.kt | 72 -------
.../kotlin/org/pacien/tincapp/commands/TincApp.kt | 74 -------
.../kotlin/org/pacien/tincapp/commands/Tincd.kt | 37 ----
.../main/kotlin/org/pacien/tincapp/context/App.kt | 85 --------
.../kotlin/org/pacien/tincapp/context/AppInfo.kt | 47 ----
.../kotlin/org/pacien/tincapp/context/AppLogger.kt | 63 ------
.../tincapp/context/AppNotificationManager.kt | 84 --------
.../kotlin/org/pacien/tincapp/context/AppPaths.kt | 71 -------
.../org/pacien/tincapp/context/CrashRecorder.kt | 48 -----
.../kotlin/org/pacien/tincapp/data/CidrAddress.kt | 39 ----
.../org/pacien/tincapp/data/TincConfiguration.kt | 41 ----
.../tincapp/data/VpnInterfaceConfiguration.kt | 92 --------
.../org/pacien/tincapp/extensions/Android.kt | 41 ----
.../tincapp/extensions/ApacheConfiguration.kt | 33 ---
.../kotlin/org/pacien/tincapp/extensions/Java.kt | 38 ----
.../pacien/tincapp/extensions/VpnServiceBuilder.kt | 80 -------
.../kotlin/org/pacien/tincapp/intent/Actions.kt | 39 ----
.../org/pacien/tincapp/intent/BroadcastMapper.kt | 38 ----
.../org/pacien/tincapp/service/TincVpnService.kt | 236 ---------------------
.../kotlin/org/pacien/tincapp/utils/PemUtils.kt | 94 --------
.../org/pacien/tincapp/utils/ProgressModal.kt | 49 -----
.../kotlin/org/pacien/tincapp/utils/TincKeyring.kt | 44 ----
29 files changed, 2396 deletions(-)
delete mode 100644 app/src/main/kotlin/org/pacien/tincapp/activities/BaseActivity.kt
delete mode 100644 app/src/main/kotlin/org/pacien/tincapp/activities/ConfigureActivity.kt
delete mode 100644 app/src/main/kotlin/org/pacien/tincapp/activities/StartActivity.kt
delete mode 100644 app/src/main/kotlin/org/pacien/tincapp/activities/StatusActivity.kt
delete mode 100644 app/src/main/kotlin/org/pacien/tincapp/activities/ViewLogActivity.kt
delete mode 100644 app/src/main/kotlin/org/pacien/tincapp/commands/Command.kt
delete mode 100644 app/src/main/kotlin/org/pacien/tincapp/commands/Executor.kt
delete mode 100644 app/src/main/kotlin/org/pacien/tincapp/commands/Tinc.kt
delete mode 100644 app/src/main/kotlin/org/pacien/tincapp/commands/TincApp.kt
delete mode 100644 app/src/main/kotlin/org/pacien/tincapp/commands/Tincd.kt
delete mode 100644 app/src/main/kotlin/org/pacien/tincapp/context/App.kt
delete mode 100644 app/src/main/kotlin/org/pacien/tincapp/context/AppInfo.kt
delete mode 100644 app/src/main/kotlin/org/pacien/tincapp/context/AppLogger.kt
delete mode 100644 app/src/main/kotlin/org/pacien/tincapp/context/AppNotificationManager.kt
delete mode 100644 app/src/main/kotlin/org/pacien/tincapp/context/AppPaths.kt
delete mode 100644 app/src/main/kotlin/org/pacien/tincapp/context/CrashRecorder.kt
delete mode 100644 app/src/main/kotlin/org/pacien/tincapp/data/CidrAddress.kt
delete mode 100644 app/src/main/kotlin/org/pacien/tincapp/data/TincConfiguration.kt
delete mode 100644 app/src/main/kotlin/org/pacien/tincapp/data/VpnInterfaceConfiguration.kt
delete mode 100644 app/src/main/kotlin/org/pacien/tincapp/extensions/Android.kt
delete mode 100644 app/src/main/kotlin/org/pacien/tincapp/extensions/ApacheConfiguration.kt
delete mode 100644 app/src/main/kotlin/org/pacien/tincapp/extensions/Java.kt
delete mode 100644 app/src/main/kotlin/org/pacien/tincapp/extensions/VpnServiceBuilder.kt
delete mode 100644 app/src/main/kotlin/org/pacien/tincapp/intent/Actions.kt
delete mode 100644 app/src/main/kotlin/org/pacien/tincapp/intent/BroadcastMapper.kt
delete mode 100644 app/src/main/kotlin/org/pacien/tincapp/service/TincVpnService.kt
delete mode 100644 app/src/main/kotlin/org/pacien/tincapp/utils/PemUtils.kt
delete mode 100644 app/src/main/kotlin/org/pacien/tincapp/utils/ProgressModal.kt
delete mode 100644 app/src/main/kotlin/org/pacien/tincapp/utils/TincKeyring.kt
(limited to 'app/src/main/kotlin/org')
diff --git a/app/src/main/kotlin/org/pacien/tincapp/activities/BaseActivity.kt b/app/src/main/kotlin/org/pacien/tincapp/activities/BaseActivity.kt
deleted file mode 100644
index 4dc2381..0000000
--- a/app/src/main/kotlin/org/pacien/tincapp/activities/BaseActivity.kt
+++ /dev/null
@@ -1,114 +0,0 @@
-/*
- * Tinc App, an Android binding and user interface for the tinc mesh VPN daemon
- * Copyright (C) 2017-2018 Pacien TRAN-GIRARD
- *
- * This program is free software: you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or
- * (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program. If not, see .
- */
-
-package org.pacien.tincapp.activities
-
-import android.os.Bundle
-import android.support.annotation.StringRes
-import android.support.design.widget.Snackbar
-import android.support.v7.app.AlertDialog
-import android.support.v7.app.AppCompatActivity
-import android.view.Menu
-import android.view.MenuItem
-import kotlinx.android.synthetic.main.base.*
-import org.pacien.tincapp.R
-import org.pacien.tincapp.context.App
-import org.pacien.tincapp.context.AppInfo
-import org.pacien.tincapp.context.AppPaths
-import org.pacien.tincapp.context.CrashRecorder
-import org.pacien.tincapp.utils.ProgressModal
-
-/**
- * @author pacien
- */
-abstract class BaseActivity : AppCompatActivity() {
- private var active = false
-
- override fun onCreate(savedInstanceState: Bundle?) {
- super.onCreate(savedInstanceState)
- setContentView(R.layout.base)
- }
-
- override fun onCreateOptionsMenu(m: Menu): Boolean {
- menuInflater.inflate(R.menu.menu_base, m)
- return true
- }
-
- override fun onStart() {
- super.onStart()
- active = true
- }
-
- override fun onResume() {
- super.onResume()
- active = true
- }
-
- override fun onPause() {
- active = false
- super.onPause()
- }
-
- override fun onStop() {
- active = false
- super.onStop()
- }
-
- fun aboutDialog(@Suppress("UNUSED_PARAMETER") i: MenuItem) {
- AlertDialog.Builder(this)
- .setTitle(resources.getString(R.string.app_name))
- .setMessage(resources.getString(R.string.app_short_desc) + "\n\n" +
- resources.getString(R.string.app_copyright) + " " +
- resources.getString(R.string.app_license) + "\n\n" +
- AppInfo.all())
- .setNeutralButton(R.string.action_open_project_website) { _, _ -> App.openURL(resources.getString(R.string.app_website_url)) }
- .setPositiveButton(R.string.action_close) { _, _ -> Unit }
- .show()
- }
-
- fun runOnUiThread(action: () -> Unit) {
- if (active) super.runOnUiThread(action)
- }
-
- fun handleRecentCrash() {
- if (!CrashRecorder.hasPreviouslyCrashed()) return
- CrashRecorder.dismissPreviousCrash()
-
- AlertDialog.Builder(this)
- .setTitle(R.string.title_app_crash)
- .setMessage(listOf(
- resources.getString(R.string.message_app_crash),
- resources.getString(R.string.message_crash_logged, AppPaths.appLogFile().absolutePath)
- ).joinToString("\n\n"))
- .setNeutralButton(R.string.action_send_report) { _, _ ->
- App.sendMail(
- resources.getString(R.string.app_dev_email),
- listOf(R.string.app_name, R.string.title_app_crash).joinToString(" / ", transform = resources::getString),
- AppPaths.appLogFile().let { if (it.exists()) it.readText() else "" })
- }
- .setPositiveButton(R.string.action_close) { _, _ -> Unit }
- .show()
- }
-
- protected fun notify(@StringRes msg: Int) = Snackbar.make(activity_base, msg, Snackbar.LENGTH_LONG).show()
- protected fun notify(msg: String) = Snackbar.make(activity_base, msg, Snackbar.LENGTH_LONG).show()
- protected fun showProgressDialog(@StringRes msg: Int): AlertDialog = ProgressModal.show(this, getString(msg))
- protected fun showErrorDialog(msg: String): AlertDialog = AlertDialog.Builder(this)
- .setTitle(R.string.title_error).setMessage(msg)
- .setPositiveButton(R.string.action_close) { _, _ -> Unit }.show()
-}
diff --git a/app/src/main/kotlin/org/pacien/tincapp/activities/ConfigureActivity.kt b/app/src/main/kotlin/org/pacien/tincapp/activities/ConfigureActivity.kt
deleted file mode 100644
index 2aab304..0000000
--- a/app/src/main/kotlin/org/pacien/tincapp/activities/ConfigureActivity.kt
+++ /dev/null
@@ -1,145 +0,0 @@
-/*
- * Tinc App, an Android binding and user interface for the tinc mesh VPN daemon
- * Copyright (C) 2017-2018 Pacien TRAN-GIRARD
- *
- * This program is free software: you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or
- * (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program. If not, see .
- */
-
-package org.pacien.tincapp.activities
-
-import android.content.Intent
-import android.os.Bundle
-import android.support.annotation.StringRes
-import android.support.v7.app.AlertDialog
-import android.view.View
-import com.google.zxing.integration.android.IntentIntegrator
-import com.google.zxing.integration.android.IntentResult
-import java8.util.concurrent.CompletableFuture
-import kotlinx.android.synthetic.main.base.*
-import kotlinx.android.synthetic.main.dialog_encrypt_decrypt_keys.view.*
-import kotlinx.android.synthetic.main.dialog_network_generate.view.*
-import kotlinx.android.synthetic.main.dialog_network_join.view.*
-import kotlinx.android.synthetic.main.page_configure.*
-import org.pacien.tincapp.R
-import org.pacien.tincapp.commands.Tinc
-import org.pacien.tincapp.commands.TincApp
-import org.pacien.tincapp.context.AppPaths
-import org.pacien.tincapp.extensions.Java.exceptionallyAccept
-import java.util.regex.Pattern
-
-/**
- * @author pacien
- */
-class ConfigureActivity : BaseActivity() {
- companion object {
- private val NETWORK_NAME_PATTERN = Pattern.compile("^[^\\x00/]*$")
- }
-
- private var joinDialog: View? = null
-
- override fun onActivityResult(requestCode: Int, resultCode: Int, data: Intent?) {
- super.onActivityResult(requestCode, resultCode, data)
-
- IntentIntegrator.parseActivityResult(requestCode, resultCode, data)
- ?.let(IntentResult::getContents)
- ?.let(String::trim)
- ?.let { joinDialog?.invitation_url?.setText(it) }
- }
-
- override fun onCreate(savedInstanceState: Bundle?) {
- super.onCreate(savedInstanceState)
- supportActionBar!!.setDisplayHomeAsUpEnabled(true)
- layoutInflater.inflate(R.layout.page_configure, main_content)
- writeContent()
- }
-
- fun scanCode(@Suppress("UNUSED_PARAMETER") v: View) {
- IntentIntegrator(this).initiateScan()
- }
-
- fun openGenerateConfDialog(@Suppress("UNUSED_PARAMETER") v: View) {
- val genDialog = layoutInflater.inflate(R.layout.dialog_network_generate, main_content, false)
- AlertDialog.Builder(this).setTitle(R.string.title_new_network).setView(genDialog)
- .setPositiveButton(R.string.action_create) { _, _ ->
- generateConf(
- genDialog.new_net_name.text.toString(),
- genDialog.new_node_name.text.toString(),
- genDialog.new_passphrase.text.toString())
- }.setNegativeButton(R.string.action_cancel) { _, _ -> Unit }.show()
- }
-
- fun openJoinNetworkDialog(@Suppress("UNUSED_PARAMETER") v: View) {
- joinDialog = layoutInflater.inflate(R.layout.dialog_network_join, main_content, false)
- AlertDialog.Builder(this).setTitle(R.string.title_join_network).setView(joinDialog)
- .setPositiveButton(R.string.action_join) { _, _ ->
- joinNetwork(
- joinDialog!!.net_name.text.toString(),
- joinDialog!!.invitation_url.text.toString(),
- joinDialog!!.join_passphrase.text.toString())
- }.setNegativeButton(R.string.action_cancel) { _, _ -> Unit }.show()
- }
-
- fun openEncryptDecryptPrivateKeyDialog(@Suppress("UNUSED_PARAMETER") v: View) {
- val encryptDecryptDialog = layoutInflater.inflate(R.layout.dialog_encrypt_decrypt_keys, main_content, false)
- AlertDialog.Builder(this).setTitle(R.string.title_private_keys_encryption).setView(encryptDecryptDialog)
- .setPositiveButton(R.string.action_apply) { _, _ ->
- encryptDecryptPrivateKeys(
- encryptDecryptDialog!!.enc_dec_net_name.text.toString(),
- encryptDecryptDialog.enc_dec_current_passphrase.text.toString(),
- encryptDecryptDialog.enc_dec_new_passphrase.text.toString())
- }.setNegativeButton(R.string.action_cancel) { _, _ -> Unit }.show()
- }
-
- private fun writeContent() {
- text_configuration_directory.text = AppPaths.confDir().absolutePath
- text_log_directory.text = AppPaths.cacheDir().absolutePath
- text_tinc_binary.text = AppPaths.tinc().absolutePath
- }
-
- private fun generateConf(netName: String, nodeName: String, passphrase: String? = null) = execAction(
- R.string.message_generating_configuration,
- validateNetName(netName)
- .thenCompose { Tinc.init(netName, nodeName) }
- .thenCompose { TincApp.removeScripts(netName) }
- .thenCompose { TincApp.generateIfaceCfgTemplate(netName) }
- .thenCompose { TincApp.setPassphrase(netName, newPassphrase = passphrase) })
-
- private fun joinNetwork(netName: String, url: String, passphrase: String? = null) = execAction(
- R.string.message_joining_network,
- validateNetName(netName)
- .thenCompose { Tinc.join(netName, url) }
- .thenCompose { TincApp.removeScripts(netName) }
- .thenCompose { TincApp.generateIfaceCfg(netName) }
- .thenCompose { TincApp.setPassphrase(netName, newPassphrase = passphrase) })
-
- private fun encryptDecryptPrivateKeys(netName: String, currentPassphrase: String, newPassphrase: String) = execAction(
- R.string.message_encrypting_decrypting_private_keys,
- validateNetName(netName)
- .thenCompose { TincApp.setPassphrase(netName, currentPassphrase, newPassphrase) })
-
- private fun execAction(@StringRes label: Int, action: CompletableFuture) {
- showProgressDialog(label).let { progressDialog ->
- action
- .whenComplete { _, _ -> progressDialog.dismiss() }
- .thenAccept { notify(R.string.message_network_configuration_written) }
- .exceptionallyAccept { runOnUiThread { showErrorDialog(it.cause!!.localizedMessage) } }
- }
- }
-
- private fun validateNetName(netName: String): CompletableFuture =
- if (NETWORK_NAME_PATTERN.matcher(netName).matches())
- CompletableFuture.completedFuture(Unit)
- else
- CompletableFuture.failedFuture(IllegalArgumentException(resources.getString(R.string.message_invalid_network_name)))
-}
diff --git a/app/src/main/kotlin/org/pacien/tincapp/activities/StartActivity.kt b/app/src/main/kotlin/org/pacien/tincapp/activities/StartActivity.kt
deleted file mode 100644
index 50e002f..0000000
--- a/app/src/main/kotlin/org/pacien/tincapp/activities/StartActivity.kt
+++ /dev/null
@@ -1,201 +0,0 @@
-/*
- * Tinc App, an Android binding and user interface for the tinc mesh VPN daemon
- * Copyright (C) 2017-2018 Pacien TRAN-GIRARD
- *
- * This program is free software: you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or
- * (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program. If not, see .
- */
-
-package org.pacien.tincapp.activities
-
-import android.app.Activity
-import android.content.Intent
-import android.net.VpnService
-import android.os.Bundle
-import android.support.v4.widget.SwipeRefreshLayout
-import android.support.v7.app.AlertDialog
-import android.view.Menu
-import android.view.MenuItem
-import android.view.View
-import android.widget.AdapterView
-import android.widget.ArrayAdapter
-import android.widget.TextView
-import kotlinx.android.synthetic.main.base.*
-import kotlinx.android.synthetic.main.dialog_decrypt_keys.view.*
-import kotlinx.android.synthetic.main.fragment_list_view.*
-import kotlinx.android.synthetic.main.fragment_network_list_header.*
-import org.pacien.tincapp.R
-import org.pacien.tincapp.context.AppPaths
-import org.pacien.tincapp.extensions.Android.setElements
-import org.pacien.tincapp.intent.Actions
-import org.pacien.tincapp.intent.BroadcastMapper
-import org.pacien.tincapp.service.TincVpnService
-import org.pacien.tincapp.utils.TincKeyring
-
-/**
- * @author pacien
- */
-class StartActivity : BaseActivity() {
- companion object {
- private const val PERMISSION_REQUEST = 0
- }
-
- private val networkList = object : AdapterView.OnItemClickListener, SwipeRefreshLayout.OnRefreshListener {
- private var networkListAdapter: ArrayAdapter? = null
-
- fun init() {
- networkListAdapter = ArrayAdapter(this@StartActivity, R.layout.fragment_list_item)
- layoutInflater.inflate(R.layout.fragment_list_view, main_content)
- list_wrapper.setOnRefreshListener(this)
- list.addHeaderView(layoutInflater.inflate(R.layout.fragment_network_list_header, list, false), null, false)
- list.addFooterView(View(this@StartActivity), null, false)
- list.adapter = networkListAdapter
- list.onItemClickListener = this
- }
-
- fun destroy() {
- networkListAdapter = null
- }
-
- override fun onRefresh() {
- val networks = AppPaths.confDir().list()?.sorted() ?: emptyList()
- runOnUiThread {
- networkListAdapter?.setElements(networks)
- setPlaceholderVisibility()
- list_wrapper.isRefreshing = false
- }
- }
-
- override fun onItemClick(parent: AdapterView<*>?, view: View?, position: Int, id: Long) {
- connectionStarter.tryStart(netName = (view as TextView).text.toString(), displayStatus = true)
- }
-
- private fun setPlaceholderVisibility() = if (networkListAdapter?.isEmpty != false) {
- network_list_placeholder.text = getListPlaceholderText()
- network_list_placeholder.visibility = View.VISIBLE
- } else {
- network_list_placeholder.visibility = View.GONE
- }
-
- private fun getListPlaceholderText() = if (!AppPaths.storageAvailable()) {
- getText(R.string.message_storage_unavailable)
- } else {
- getText(R.string.message_no_network_configuration_found)
- }
- }
-
- private val connectionStarter = object {
- private var netName: String? = null
- private var passphrase: String? = null
- private var displayStatus = false
-
- fun displayStatus() = displayStatus
-
- fun tryStart(netName: String? = null, passphrase: String? = null, displayStatus: Boolean? = null) {
- if (netName != null) this.netName = netName
- this.passphrase = passphrase
- if (displayStatus != null) this.displayStatus = displayStatus
-
- val permissionRequestIntent = VpnService.prepare(this@StartActivity)
- if (permissionRequestIntent != null)
- return startActivityForResult(permissionRequestIntent, PERMISSION_REQUEST)
-
- if (TincKeyring.needsPassphrase(this.netName!!) && this.passphrase == null)
- return askForPassphrase()
-
- startVpn(this.netName!!, this.passphrase)
- }
-
- private fun askForPassphrase() {
- layoutInflater.inflate(R.layout.dialog_decrypt_keys, main_content, false).let { dialog ->
- AlertDialog.Builder(this@StartActivity)
- .setTitle(R.string.title_unlock_private_keys).setView(dialog)
- .setPositiveButton(R.string.action_unlock) { _, _ -> tryStart(passphrase = dialog.passphrase.text.toString()) }
- .setNegativeButton(R.string.action_cancel) { _, _ -> Unit }
- .show()
- }
- }
-
- private fun startVpn(netName: String, passphrase: String? = null) {
- connectDialog = showProgressDialog(R.string.message_starting_vpn)
- TincVpnService.connect(netName, passphrase)
- }
- }
-
- private val broadcastMapper = BroadcastMapper(mapOf(
- Actions.EVENT_CONNECTED to this::onVpnStart,
- Actions.EVENT_ABORTED to this::onVpnStartError))
-
- private var connectDialog: AlertDialog? = null
-
- override fun onCreate(savedInstanceState: Bundle?) {
- super.onCreate(savedInstanceState)
- networkList.init()
-
- if (intent.action == Actions.ACTION_CONNECT && intent.data?.schemeSpecificPart != null)
- connectionStarter.tryStart(intent.data.schemeSpecificPart, intent.data.fragment, false)
- }
-
- override fun onCreateOptionsMenu(m: Menu): Boolean {
- menuInflater.inflate(R.menu.menu_start, m)
- return super.onCreateOptionsMenu(m)
- }
-
- override fun onDestroy() {
- networkList.destroy()
- connectDialog?.dismiss()
- super.onDestroy()
- }
-
- override fun onStart() {
- super.onStart()
- networkList.onRefresh()
- }
-
- override fun onResume() {
- super.onResume()
- if (TincVpnService.isConnected()) openStatusActivity(false)
- broadcastMapper.register()
- handleRecentCrash()
- }
-
- override fun onPause() {
- broadcastMapper.unregister()
- super.onPause()
- }
-
- override fun onActivityResult(request: Int, result: Int, data: Intent?): Unit = when (request) {
- PERMISSION_REQUEST -> if (result == Activity.RESULT_OK) connectionStarter.tryStart() else Unit
- else -> throw IllegalArgumentException("Result for unknown request received.")
- }
-
- fun openConfigureActivity(@Suppress("UNUSED_PARAMETER") i: MenuItem) =
- startActivity(Intent(this, ConfigureActivity::class.java))
-
- private fun onVpnStart() {
- connectDialog?.dismiss()
- if (connectionStarter.displayStatus()) openStatusActivity()
- finish()
- }
-
- private fun onVpnStartError() {
- connectDialog?.dismiss()
- }
-
- private fun openStatusActivity(transition: Boolean = true) =
- startActivity(
- Intent(this, StatusActivity::class.java)
- .addFlags(Intent.FLAG_ACTIVITY_NEW_TASK)
- .addFlags(Intent.FLAG_ACTIVITY_CLEAR_TASK)
- .apply { if (!transition) addFlags(Intent.FLAG_ACTIVITY_NO_ANIMATION) })
-}
diff --git a/app/src/main/kotlin/org/pacien/tincapp/activities/StatusActivity.kt b/app/src/main/kotlin/org/pacien/tincapp/activities/StatusActivity.kt
deleted file mode 100644
index 68e008e..0000000
--- a/app/src/main/kotlin/org/pacien/tincapp/activities/StatusActivity.kt
+++ /dev/null
@@ -1,196 +0,0 @@
-/*
- * Tinc App, an Android binding and user interface for the tinc mesh VPN daemon
- * Copyright (C) 2017-2018 Pacien TRAN-GIRARD
- *
- * This program is free software: you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or
- * (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program. If not, see .
- */
-
-package org.pacien.tincapp.activities
-
-import android.content.Intent
-import android.os.Bundle
-import android.support.v4.widget.SwipeRefreshLayout
-import android.support.v7.app.AlertDialog
-import android.view.Menu
-import android.view.MenuItem
-import android.view.View
-import android.widget.AdapterView
-import android.widget.ArrayAdapter
-import android.widget.TextView
-import java8.util.concurrent.CompletableFuture
-import kotlinx.android.synthetic.main.base.*
-import kotlinx.android.synthetic.main.dialog_node_details.view.*
-import kotlinx.android.synthetic.main.fragment_list_view.*
-import kotlinx.android.synthetic.main.fragment_network_status_header.*
-import org.pacien.tincapp.R
-import org.pacien.tincapp.commands.Executor
-import org.pacien.tincapp.commands.Tinc
-import org.pacien.tincapp.data.VpnInterfaceConfiguration
-import org.pacien.tincapp.extensions.Android.setElements
-import org.pacien.tincapp.extensions.Android.setText
-import org.pacien.tincapp.intent.Actions
-import org.pacien.tincapp.intent.BroadcastMapper
-import org.pacien.tincapp.service.TincVpnService
-import java.util.*
-import kotlin.concurrent.timerTask
-
-/**
- * @author pacien
- */
-class StatusActivity : BaseActivity(), AdapterView.OnItemClickListener, SwipeRefreshLayout.OnRefreshListener {
- private val broadcastMapper = BroadcastMapper(mapOf(Actions.EVENT_DISCONNECTED to this::onVpnShutdown))
- private var shutdownDialog: AlertDialog? = null
- private var nodeListAdapter: ArrayAdapter? = null
- private var refreshTimer: Timer? = null
- private var listNetworksAfterExit = true
-
- override fun onCreate(savedInstanceState: Bundle?) {
- super.onCreate(savedInstanceState)
- nodeListAdapter = ArrayAdapter(this, R.layout.fragment_list_item)
-
- layoutInflater.inflate(R.layout.fragment_list_view, main_content)
- list_wrapper.setOnRefreshListener(this)
- list.addHeaderView(layoutInflater.inflate(R.layout.fragment_network_status_header, list, false), null, false)
- list.addFooterView(View(this), null, false)
- list.onItemClickListener = this
- list.adapter = nodeListAdapter
-
- if (intent.action == Actions.ACTION_DISCONNECT) {
- listNetworksAfterExit = false
- stopVpn()
- } else {
- listNetworksAfterExit = true
- }
- }
-
- override fun onCreateOptionsMenu(m: Menu): Boolean {
- menuInflater.inflate(R.menu.menu_status, m)
- return super.onCreateOptionsMenu(m)
- }
-
- override fun onDestroy() {
- super.onDestroy()
- nodeListAdapter = null
- refreshTimer = null
- }
-
- override fun onStart() {
- super.onStart()
- refreshTimer = Timer(true)
- refreshTimer?.schedule(timerTask { updateView() }, NOW, REFRESH_RATE)
- writeNetworkInfo(TincVpnService.getCurrentInterfaceCfg() ?: VpnInterfaceConfiguration())
- }
-
- override fun onStop() {
- refreshTimer?.cancel()
- super.onStop()
- }
-
- override fun onResume() {
- super.onResume()
- broadcastMapper.register()
- updateView()
- handleRecentCrash()
- }
-
- override fun onPause() {
- broadcastMapper.unregister()
- super.onPause()
- }
-
- override fun onRefresh() {
- refreshTimer?.schedule(timerTask { updateView() }, NOW)
- }
-
- override fun onItemClick(parent: AdapterView<*>?, view: View?, position: Int, id: Long) = when (view) {
- is TextView -> showNodeInfo(view.text.toString())
- else -> Unit
- }
-
- private fun onVpnShutdown() {
- shutdownDialog?.dismiss()
- if (listNetworksAfterExit) openStartActivity()
- finish()
- }
-
- fun stopVpn(@Suppress("UNUSED_PARAMETER") i: MenuItem? = null) {
- refreshTimer?.cancel()
- list_wrapper.isRefreshing = false
- shutdownDialog = showProgressDialog(R.string.message_disconnecting_vpn)
- TincVpnService.disconnect()
- }
-
- fun openLogViewer(@Suppress("UNUSED_PARAMETER") i: MenuItem) =
- startActivity(Intent(this, ViewLogActivity::class.java))
-
- private fun writeNetworkInfo(cfg: VpnInterfaceConfiguration) {
- text_network_name.text = TincVpnService.getCurrentNetName() ?: getString(R.string.value_none)
- text_network_ip_addresses.setText(cfg.addresses.map { it.toSlashSeparated() })
- text_network_routes.setText(cfg.routes.map { it.toSlashSeparated() })
- text_network_dns_servers.setText(cfg.dnsServers)
- text_network_search_domains.setText(cfg.searchDomains)
- text_network_allow_bypass.text = getString(if (cfg.allowBypass) R.string.value_yes else R.string.value_no)
- block_network_allowed_applications.visibility = if (cfg.allowedApplications.isNotEmpty()) View.VISIBLE else View.GONE
- text_network_allowed_applications.setText(cfg.allowedApplications)
- block_network_disallowed_applications.visibility = if (cfg.disallowedApplications.isNotEmpty()) View.VISIBLE else View.GONE
- text_network_disallowed_applications.setText(cfg.disallowedApplications)
- }
-
- private fun writeNodeList(nodeList: List) {
- nodeListAdapter?.setElements(nodeList)
- node_list_placeholder.visibility = View.GONE
- list_wrapper.isRefreshing = false
- }
-
- private fun updateNodeList() {
- getNodeNames().thenAccept { nodeList -> runOnUiThread { writeNodeList(nodeList) } }
- }
-
- private fun showNodeInfo(nodeName: String) {
- val dialogTextView = layoutInflater.inflate(R.layout.dialog_node_details, main_content, false)
-
- runOnUiThread {
- AlertDialog.Builder(this)
- .setTitle(R.string.title_node_info)
- .setView(dialogTextView)
- .setPositiveButton(R.string.action_close) { _, _ -> Unit }
- .show()
- }
-
- TincVpnService.getCurrentNetName()?.let { netName ->
- Tinc.info(netName, nodeName).thenAccept { nodeInfo ->
- runOnUiThread { dialogTextView.dialog_node_details.text = nodeInfo }
- }
- }
- }
-
- private fun updateView() = when {
- TincVpnService.isConnected() -> updateNodeList()
- else -> openStartActivity()
- }
-
- private fun openStartActivity() {
- startActivity(Intent(this, StartActivity::class.java).addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP))
- finish()
- }
-
- companion object {
- private const val REFRESH_RATE = 5000L
- private const val NOW = 0L
-
- fun getNodeNames(): CompletableFuture> = TincVpnService.getCurrentNetName()?.let { netName ->
- Tinc.dumpNodes(netName).thenApply> { list -> list.map { it.substringBefore(' ') } }
- } ?: Executor.supplyAsyncTask> { emptyList() }
- }
-}
diff --git a/app/src/main/kotlin/org/pacien/tincapp/activities/ViewLogActivity.kt b/app/src/main/kotlin/org/pacien/tincapp/activities/ViewLogActivity.kt
deleted file mode 100644
index f3f7e24..0000000
--- a/app/src/main/kotlin/org/pacien/tincapp/activities/ViewLogActivity.kt
+++ /dev/null
@@ -1,164 +0,0 @@
-/*
- * Tinc App, an Android binding and user interface for the tinc mesh VPN daemon
- * Copyright (C) 2017-2018 Pacien TRAN-GIRARD
- *
- * This program is free software: you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or
- * (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program. If not, see .
- */
-
-package org.pacien.tincapp.activities
-
-import android.content.Intent
-import android.os.Bundle
-import android.view.Menu
-import android.view.MenuItem
-import android.view.View
-import android.widget.ScrollView
-import kotlinx.android.synthetic.main.base.*
-import kotlinx.android.synthetic.main.page_viewlog.*
-import org.pacien.tincapp.R
-import org.pacien.tincapp.commands.Executor
-import org.pacien.tincapp.commands.Tinc
-import org.pacien.tincapp.service.TincVpnService
-import java.util.*
-import kotlin.concurrent.timer
-
-/**
- * @author pacien
- */
-class ViewLogActivity : BaseActivity() {
- companion object {
- private const val LOG_LINES = 250
- private const val LOG_LEVEL = 5
- private const val NEW_LINE = "\n"
- private const val SPACED_NEW_LINE = "\n\n"
- private const val UPDATE_INTERVAL = 250L // ms
- private const val MIME_TYPE = "text/plain"
- }
-
- private val log = LinkedList()
- private var logUpdateTimer: Timer? = null
- private var logger: Process? = null
- private var toggleButton: MenuItem? = null
-
- override fun onCreate(savedInstanceState: Bundle?) {
- super.onCreate(savedInstanceState)
- supportActionBar!!.setDisplayHomeAsUpEnabled(true)
- layoutInflater.inflate(R.layout.page_viewlog, main_content)
- toggleLogging(true)
- }
-
- override fun onCreateOptionsMenu(m: Menu): Boolean {
- menuInflater.inflate(R.menu.menu_viewlog, m)
- toggleButton = m.findItem(R.id.log_viewer_action_toggle)
- return super.onCreateOptionsMenu(m)
- }
-
- override fun onSupportNavigateUp(): Boolean {
- finish()
- return true
- }
-
- override fun onDestroy() {
- toggleLogging(false)
- super.onDestroy()
- }
-
- fun share(@Suppress("UNUSED_PARAMETER") menuItem: MenuItem) {
- synchronized(this) {
- val logFragment = log.joinToString(NEW_LINE)
- val shareIntent = Intent(Intent.ACTION_SEND)
- .setType(MIME_TYPE)
- .putExtra(Intent.EXTRA_TEXT, logFragment)
-
- startActivity(Intent.createChooser(shareIntent, resources.getString(R.string.menu_share_log)))
- }
- }
-
- fun toggleLogging(@Suppress("UNUSED_PARAMETER") menuItem: MenuItem) = toggleLogging(logger == null)
-
- private fun toggleLogging(enable: Boolean) {
- if (enable) {
- disableUserScroll()
- toggleButton?.setIcon(R.drawable.ic_pause_circle_outline_primary_24dp)
- startLogging()
- } else {
- enableUserScroll()
- toggleButton?.setIcon(R.drawable.ic_pause_circle_filled_primary_24dp)
- stopLogging()
- }
- }
-
- private fun startLogging(level: Int = LOG_LEVEL) {
- appendLog(resources.getString(R.string.message_log_level_set, level))
-
- TincVpnService.getCurrentNetName()?.let { netName ->
- Tinc.log(netName, level).let { process ->
- logger = process
- Executor.runAsyncTask { captureLog(process) }
- }
- logUpdateTimer = timer(period = UPDATE_INTERVAL, action = { printLog() })
- } ?: run {
- appendLog(resources.getString(R.string.message_no_daemon))
- toggleLogging(false)
- }
- }
-
- private fun stopLogging() {
- logger?.destroy()
- logger = null
- logUpdateTimer?.cancel()
- logUpdateTimer?.purge()
- logUpdateTimer = null
- appendLog(resources.getString(R.string.message_log_paused))
- printLog()
- }
-
- private fun captureLog(logger: Process) {
- logger.inputStream?.use { inputStream ->
- inputStream.bufferedReader().useLines { lines ->
- lines.forEach { appendLog(it) }
- }
- }
- }
-
- private fun appendLog(line: String) = synchronized(this) {
- if (log.size >= LOG_LINES) log.removeFirst()
- log.addLast(line)
- }
-
- private fun printLog() = synchronized(this) {
- log.joinToString(SPACED_NEW_LINE).let {
- logview_text.post {
- logview_text.text = it
- logview_frame.post { logview_frame.fullScroll(View.FOCUS_DOWN) }
- }
- }
- }
-
- private fun enableUserScroll() {
- logview_text.setTextIsSelectable(true)
- logview_frame.setState(true)
- }
-
- private fun disableUserScroll() {
- logview_text.setTextIsSelectable(false)
- logview_frame.setState(false)
- }
-
- private fun ScrollView.setState(enabled: Boolean) {
- if (enabled) setOnTouchListener(null) else setOnTouchListener { _, _ -> true }
- logview_frame.isSmoothScrollingEnabled = enabled
- logview_frame.isVerticalScrollBarEnabled = enabled
- }
-}
diff --git a/app/src/main/kotlin/org/pacien/tincapp/commands/Command.kt b/app/src/main/kotlin/org/pacien/tincapp/commands/Command.kt
deleted file mode 100644
index 132cda9..0000000
--- a/app/src/main/kotlin/org/pacien/tincapp/commands/Command.kt
+++ /dev/null
@@ -1,46 +0,0 @@
-/*
- * Tinc App, an Android binding and user interface for the tinc mesh VPN daemon
- * Copyright (C) 2017-2018 Pacien TRAN-GIRARD
- *
- * This program is free software: you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or
- * (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program. If not, see .
- */
-
-package org.pacien.tincapp.commands
-
-import java.util.*
-
-/**
- * @author pacien
- */
-internal class Command(private val cmd: String) {
- private data class Option(val key: String, val value: String?) {
- fun toCommandLineOption(): String = if (value != null) "--$key=$value" else "--$key"
- }
-
- private val opts: MutableList