Kis*_*nki 5 security android kotlin passcode
我正在开发一个应用程序,我需要通过为用户设置密码/密码/pin 来设置安全功能,以便每当他们从后台打开应用程序时,应用程序都会要求输入密码/密码/pin。我读了一些这样的文章/解决方案,但它们对我没有帮助。我们在普通银行应用程序中发现了相同的功能,每当您打开应用程序时,他们都会要求输入密码/指纹。
我已经设置了将密码/密码保存在共享首选项中的逻辑,但我不确定何时询问。我知道我们不能用密码/pin 活动替换启动屏幕,因为有时从应用程序的 homeScreen/MainActivity 中,用户按下主页按钮,当他们再次从最近的应用程序打开应用程序时,应用程序应该要求密码/pin 来恢复应用程序使用。
任何帮助,将不胜感激。
这是一个有趣的问题,我将分享我对这个问题的想法并给出解决方案。
术语:
应用锁类型: pin/pincode/password/passcode等的通用名称(在下面的部分中,我将使用pin名称来演示)
PinActivity:用户输入 PIN 码以验证自己的屏幕
故事:
对于需要用户输入 PIN 码的应用程序,他们通常希望确保敏感信息不会被其他人泄露/窃取。因此,我们将应用程序活动分为 2 组。
正常活动:不包含任何敏感信息,通常在用户登录应用之前,例如SplashActivity、LoginActivity、RegistrationActivity、PinActivity等。
受保护的活动:包含敏感信息,通常在用户登录后,例如MainActivity、HomeActivity、UserInfoActivity等。
状况:
对于安全活动,我们必须通过显示 PinActivity 确保用户在查看内容之前始终输入其 PIN。此活动将在以下场景中显示:
[1] 当用户从正常活动打开安全活动时,例如从 SplashActivity 到 MainActivity
[2] 当用户通过点击通知打开安全活动时,例如点击通知打开 MainActivity
[3] 当用户从“最近”屏幕上点击应用程序时
[4] 当应用程序从另一个地方(例如服务、广播接收器等)启动安全活动时。
执行:
对于情况 [1] [2] 和 [4],在开始安全活动之前,我们将在原始意图的基础上添加额外内容。我将创建一个名为 IntentUtils.kt 的文件
IntentUtils.kt
const val EXTRA_IS_PIN_REQUIRED = "EXTRA_IS_PIN_REQUIRED"
fun Intent.secured(): Intent {
return this.apply {
putExtra(EXTRA_IS_PIN_REQUIRED, true)
}
}
Run Code Online (Sandbox Code Playgroud)
从正常活动、通知、服务等中使用此类。
startActivity(Intent(this, MainActivity::class.java).secured())
Run Code Online (Sandbox Code Playgroud)
对于案例 [3],我将使用 2 个 API:
ProcessLifecycleOwner:检测应用程序是否进入后台。典型的场景是用户单击设备上的主页/菜单键。
ActivityLifecycleCallbacks :依靠onActivityResumed(activity)方法检测 Activity 是否恢复。
首先,我创建一个基础活动,所有正常活动都必须从此类扩展
基本活动.kt
open class BaseActivity : AppCompatActivity() {
// This method indicates that a pin is required if
// users want to see the content inside.
open fun isPinRequired() = false
}
Run Code Online (Sandbox Code Playgroud)
其次,我创建一个安全活动,所有安全活动都必须从此类扩展
安全活动.kt
open class SecuredActivity : BaseActivity() {
override fun isPinRequired() = true
// This is useful when launch a secured activity with
// singleTop, singleTask, singleInstance launch mode
override fun onNewIntent(intent: Intent?) {
super.onNewIntent(intent)
setIntent(intent)
}
}
Run Code Online (Sandbox Code Playgroud)
第三,我创建一个从应用程序扩展的类,所有逻辑都在这个类中
我的应用程序.kt
class MyApplication : Application() {
private var wasEnterBackground = false
override fun onCreate() {
super.onCreate()
registerActivityLifecycleCallbacks(ActivityLifecycleCallbacksImpl())
ProcessLifecycleOwner.get().lifecycle.addObserver(LifecycleObserverImpl())
}
private fun showPinActivity() {
startActivity(Intent(this, PinActivity::class.java))
}
inner class LifecycleObserverImpl : LifecycleObserver {
@OnLifecycleEvent(Lifecycle.Event.ON_STOP)
fun onEnterBackground() {
wasEnterBackground = true
}
}
inner class ActivityLifecycleCallbacksImpl : ActivityLifecycleCallbacks {
override fun onActivityResumed(activity: Activity) {
val baseActivity = activity as BaseActivity
if (!wasEnterBackground) {
// Handle case [1] [2] and [4]
val removed = removeIsPinRequiredKeyFromActivity(activity)
if (removed) {
showPinActivity()
}
} else {
// Handle case [3]
wasEnterBackground = false
if (baseActivity.isPinRequired()) {
removeIsPinRequiredKeyFromActivity(activity)
showPinActivity()
}
}
}
private fun removeIsPinRequiredKeyFromActivity(activity: Activity): Boolean {
val key = EXTRA_IS_PIN_REQUIRED
if (activity.intent.hasExtra(key)) {
activity.intent.removeExtra(key)
return true
}
return false
}
override fun onActivityCreated(activity: Activity, savedInstanceState: Bundle?) {}
override fun onActivityStarted(activity: Activity) {}
override fun onActivityPaused(activity: Activity) {}
override fun onActivitySaveInstanceState(activity: Activity, outState: Bundle) {}
override fun onActivityStopped(activity: Activity) {}
override fun onActivityDestroyed(activity: Activity) {}
}
}
Run Code Online (Sandbox Code Playgroud)
结论:
该解决方案适用于我之前提到的那些情况,但我尚未测试以下场景:
| 归档时间: |
|
| 查看次数: |
3216 次 |
| 最近记录: |