feat(logging): stragglers -> AppLog (#330)
Migrate RestartActivity's one raw Log.w site to AppLog, clearing the final raw android.util.Log site outside the auth/lock, DB/keystore, connectivity/send, and sync-engine migration areas so the codebase is ready for the detekt android.util.Log guard (#331). RestartActivity runs in the separate :restart trampoline process, where LibreMailApplication.onCreate returns early and never calls AppLog.install, so this breadcrumb reaches Logcat only, never a DebugReport. The migration is guard-compliance + Logcat-consistency only; behavior is unchanged since AppLog forwards to Logcat. RestartActivity is DEVICE-ONLY (multi-process kill/relaunch), so a JVM buffer-capture test doesn't apply here. Added RestartActivityLoggingTest, which instead pins the null-buffer shape this call runs under in the trampoline process: it forwards to Logcat and no-ops the buffer cleanly. Closes #330 Part of #324 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
This commit is contained in:
@@ -5,7 +5,7 @@ import android.app.Activity
|
|||||||
import android.content.Intent
|
import android.content.Intent
|
||||||
import android.os.Bundle
|
import android.os.Bundle
|
||||||
import android.os.Process
|
import android.os.Process
|
||||||
import android.util.Log
|
import org.libremail.reporting.AppLog
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Separate-process trampoline that performs an app relaunch from OUTSIDE the process being killed.
|
* Separate-process trampoline that performs an app relaunch from OUTSIDE the process being killed.
|
||||||
@@ -40,7 +40,10 @@ class RestartActivity : Activity() {
|
|||||||
if (launchIntent != null) {
|
if (launchIntent != null) {
|
||||||
startActivity(launchIntent)
|
startActivity(launchIntent)
|
||||||
} else {
|
} else {
|
||||||
Log.w(TAG, "no launch intent for $packageName; cannot relaunch after restart")
|
// Logcat-only here: this runs in the ":restart" trampoline process, where
|
||||||
|
// LibreMailApplication.onCreate returns early and never calls AppLog.install, so the
|
||||||
|
// buffer is null and this breadcrumb never reaches a DebugReport.
|
||||||
|
AppLog.w(TAG, "no launch intent for $packageName; cannot relaunch after restart")
|
||||||
}
|
}
|
||||||
|
|
||||||
finish()
|
finish()
|
||||||
|
|||||||
@@ -0,0 +1,52 @@
|
|||||||
|
// SPDX-License-Identifier: GPL-3.0-or-later
|
||||||
|
package org.libremail.restart
|
||||||
|
|
||||||
|
import android.util.Log
|
||||||
|
import io.mockk.every
|
||||||
|
import io.mockk.mockkStatic
|
||||||
|
import io.mockk.unmockkAll
|
||||||
|
import io.mockk.verify
|
||||||
|
import org.junit.After
|
||||||
|
import org.junit.Before
|
||||||
|
import org.junit.Test
|
||||||
|
import org.libremail.reporting.AppLog
|
||||||
|
import kotlin.test.assertNull
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Pins the #330 migration of [RestartActivity]'s one log site from raw `Log.w` to [AppLog.w].
|
||||||
|
* [RestartActivity] itself is DEVICE-ONLY (multi-process kill/relaunch; see its KDoc) and can't be
|
||||||
|
* exercised in a JVM test, so this characterizes the call it now makes instead of the class itself.
|
||||||
|
*
|
||||||
|
* That call runs in the ":restart" trampoline process, where `LibreMailApplication.onCreate` returns
|
||||||
|
* early and never reaches `AppLog.install` — so [AppLog]'s buffer is null there, and this breadcrumb
|
||||||
|
* reaches Logcat only, never a `DebugReport`. This is the one migrated site in the #324 epic whose
|
||||||
|
* "buffer captured the breadcrumb" assertion intentionally does not apply (see #330); instead this
|
||||||
|
* asserts the null-buffer shape: the call still forwards to Logcat and no-ops cleanly, matching the
|
||||||
|
* raw `Log.w` behavior it replaced.
|
||||||
|
*/
|
||||||
|
class RestartActivityLoggingTest {
|
||||||
|
|
||||||
|
// Mirrors RestartActivity's private TAG/message exactly (kept private there; duplicated here
|
||||||
|
// rather than widening its visibility just for this test).
|
||||||
|
private val tag = "LibreMailRestart"
|
||||||
|
private val message = "no launch intent for org.libremail.app; cannot relaunch after restart"
|
||||||
|
|
||||||
|
@Before
|
||||||
|
fun setUp() {
|
||||||
|
mockkStatic(Log::class)
|
||||||
|
every { Log.w(any<String>(), any<String>()) } returns 0
|
||||||
|
AppLog::class.java.getDeclaredField("buffer").apply { isAccessible = true }.set(AppLog, null)
|
||||||
|
}
|
||||||
|
|
||||||
|
@After
|
||||||
|
fun tearDown() = unmockkAll()
|
||||||
|
|
||||||
|
@Test
|
||||||
|
fun `RestartActivity's no-launch-intent warning forwards to Logcat and no-ops with no buffer installed`() {
|
||||||
|
AppLog.w(tag, message)
|
||||||
|
|
||||||
|
verify { Log.w(tag, message) }
|
||||||
|
val bufferField = AppLog::class.java.getDeclaredField("buffer").apply { isAccessible = true }
|
||||||
|
assertNull(bufferField.get(AppLog), "the :restart process never installs a buffer; AppLog must not create one")
|
||||||
|
}
|
||||||
|
}
|
||||||
Reference in New Issue
Block a user