manager: mount modules webui resources to manager directly.

This commit is contained in:
weishu 2024-02-22 16:01:03 +08:00
parent 9c4d20c0f2
commit 329010a694
3 changed files with 15 additions and 35 deletions

View File

@ -5,6 +5,7 @@ import coil.Coil
import coil.ImageLoader
import me.zhanghai.android.appiconloader.coil.AppIconFetcher
import me.zhanghai.android.appiconloader.coil.AppIconKeyer
import java.io.File
lateinit var ksuApp: KernelSUApplication
@ -24,6 +25,11 @@ class KernelSUApplication : Application() {
}
.build()
)
val webroot = File(dataDir, "webroot")
if (!webroot.exists()) {
webroot.mkdir()
}
}

View File

@ -15,34 +15,26 @@ import androidx.compose.runtime.DisposableEffect
import androidx.compose.runtime.LaunchedEffect
import androidx.compose.ui.Modifier
import androidx.compose.ui.platform.LocalContext
import androidx.compose.ui.platform.LocalLifecycleOwner
import androidx.core.view.WindowCompat
import androidx.core.view.WindowInsetsCompat
import androidx.core.view.WindowInsetsControllerCompat
import androidx.lifecycle.lifecycleScope
import com.google.accompanist.web.WebView
import com.google.accompanist.web.rememberWebViewState
import com.ramcosta.composedestinations.annotation.Destination
import com.ramcosta.composedestinations.navigation.DestinationsNavigator
import com.topjohnwu.superuser.ShellUtils
import kotlinx.coroutines.Dispatchers
import kotlinx.coroutines.launch
import kotlinx.coroutines.withContext
import me.weishu.kernelsu.ui.util.createRootShell
import me.weishu.kernelsu.ui.util.serveModule
import java.net.ServerSocket
@SuppressLint("SetJavaScriptEnabled")
@Destination
@Composable
fun WebScreen(navigator: DestinationsNavigator, moduleId: String, moduleName: String) {
val port = 8080
LaunchedEffect(Unit) {
serveModule(moduleId, port)
serveModule(moduleId)
}
val lifecycleOwner = LocalLifecycleOwner.current
val context = LocalContext.current
DisposableEffect(Unit) {
@ -50,15 +42,12 @@ fun WebScreen(navigator: DestinationsNavigator, moduleId: String, moduleName: St
if (WebViewInterface.isHideSystemUI && context is Activity) {
showSystemUI(context.window)
}
lifecycleOwner.lifecycleScope.launch {
stopServer(port)
}
}
}
Scaffold { innerPadding ->
WebView(
state = rememberWebViewState(url = "http://localhost:$port"),
state = rememberWebViewState(url = "file:///data/data/me.weishu.kernelsu/webroot/index.html"),
Modifier
.fillMaxSize()
.padding(innerPadding),
@ -66,6 +55,7 @@ fun WebScreen(navigator: DestinationsNavigator, moduleId: String, moduleName: St
android.webkit.WebView(context).apply {
settings.javaScriptEnabled = true
settings.domStorageEnabled = true
settings.allowFileAccess = true
addJavascriptInterface(WebViewInterface(context), "ksu")
}
})
@ -100,22 +90,6 @@ class WebViewInterface(val context: Context) {
}
private suspend fun getFreePort(): Int {
return withContext(Dispatchers.IO) {
ServerSocket(0).use { socket -> socket.localPort }
}
}
private suspend fun stopServer(port: Int) {
withContext(Dispatchers.IO) {
runCatching {
okhttp3.OkHttpClient()
.newCall(okhttp3.Request.Builder().url("http://localhost:$port/stop").build())
.execute()
}
}
}
private fun hideSystemUI(window: Window) {
WindowCompat.setDecorFitsSystemWindows(window, false)
WindowInsetsControllerCompat(window, window.decorView).let { controller ->

View File

@ -131,13 +131,13 @@ fun installModule(
}
}
fun serveModule(id: String, port: Int): Process {
fun serveModule(id: String): Boolean {
// we should use a new root shell to avoid blocking the global shell
val process = Runtime.getRuntime().exec("${getKsuDaemonPath()} debug su")
val builder = Shell.Builder.create()
val shell = builder.build(process)
shell.newJob().add("${getKsuDaemonPath()} module serve $id $port").submit()
return process
val shell = createRootShell()
return ShellUtils.fastCmdResult(
shell,
"${getKsuDaemonPath()} module link-manager $id ${android.os.Process.myPid()} ${BuildConfig.APPLICATION_ID}"
)
}
fun reboot(reason: String = "") {