stable login and check cookies

This commit is contained in:
2024-09-29 15:33:39 +03:00
parent e32b4feeef
commit e8ed594b9f
12 changed files with 162 additions and 54 deletions
@@ -25,7 +25,18 @@ class LksRepositoryImpl @Inject constructor(
): Map<String, String> = signInLks(username, password)
override suspend fun cookiesIsValid(cookie: Map<String, String>): Boolean {
return false
if(cookie.isEmpty()) return false
val document = getProfilePage(LksRequest(), cookie, 1)
println(document.body())
val pages =
document.select("body > div.container > div.bx-pagination > div > ul > li:nth-child(6) > a > span")
.text()
return pages.isNotEmpty()
}
@@ -12,5 +12,5 @@ data class LksRequest(
* Метод для получения пути после https://lk.mirea.ru/staff/students? ...
*/
fun getSubmitUrlPath(sesid: String) =
"sessid=$sesid&findname=${student}&findgroup=${group ?: ""}&finddepartment=${department ?: ""}&submit-filter=Найти"
"sessid=$sesid&findname=${student ?: ""}&findgroup=${group ?: ""}&finddepartment=${department ?: ""}&submit-filter=Найти"
}
@@ -9,6 +9,7 @@ import androidx.compose.runtime.Composable
import androidx.compose.runtime.remember
import androidx.compose.ui.Modifier
import androidx.compose.ui.res.painterResource
import androidx.compose.ui.unit.Dp
import kotlin.concurrent.thread
@OptIn(ExperimentalFoundationApi::class)
@@ -7,6 +7,7 @@ import androidx.compose.ui.unit.dp
import cafe.adriel.voyager.core.screen.Screen
import cafe.adriel.voyager.navigator.Navigator
import cafe.adriel.voyager.navigator.bottomSheet.BottomSheetNavigator
import cafe.adriel.voyager.transitions.SlideTransition
import ru.megboyzz.lks.profile.ui.screens.SearchScreen
@Composable
@@ -14,7 +15,8 @@ fun MainNavigator(screen: Screen) {
BottomSheetNavigator(
sheetShape = RoundedCornerShape(12.dp)
) {
Navigator(screen)
Navigator(screen) {
SlideTransition(it)
}
}
}
@@ -40,6 +40,7 @@ import androidx.compose.runtime.setValue
import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.draw.clip
import androidx.compose.ui.graphics.Color
import androidx.compose.ui.graphics.painter.Painter
import androidx.compose.ui.graphics.vector.ImageVector
import androidx.compose.ui.layout.onSizeChanged
@@ -264,7 +265,7 @@ fun ContextMenuButton(
Box(
modifier = Modifier
.padding(8.dp)
.clickableWithNormalRipple(onClick)
.clickableWithNormalRipple(onClick = onClick)
) {
Row(
modifier = Modifier.fillMaxWidth(),
@@ -278,7 +279,8 @@ fun ContextMenuButton(
) {
Icon(
painter = icon,
contentDescription = null
contentDescription = null,
tint = Color.Unspecified
)
Text(text = label)
}
@@ -14,6 +14,8 @@ import androidx.compose.foundation.layout.WindowInsets
import androidx.compose.foundation.layout.defaultMinSize
import androidx.compose.foundation.layout.fillMaxWidth
import androidx.compose.foundation.layout.padding
import androidx.compose.foundation.lazy.LazyColumn
import androidx.compose.foundation.lazy.items
import androidx.compose.foundation.shape.RoundedCornerShape
import androidx.compose.material.icons.Icons
import androidx.compose.material.icons.filled.Search
@@ -35,6 +37,7 @@ import androidx.compose.runtime.remember
import androidx.compose.runtime.setValue
import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.draw.clip
import androidx.compose.ui.graphics.Brush
import androidx.compose.ui.graphics.Color
import androidx.compose.ui.tooling.preview.Preview
@@ -43,6 +46,7 @@ import ru.megboyzz.lks.profile.MainActivity
import ru.megboyzz.lks.profile.domain.entities.LksResponse
import ru.megboyzz.lks.profile.domain.entities.LksStudent
import ru.megboyzz.lks.profile.ui.clickableWithNormalRipple
import ru.megboyzz.lks.profile.ui.screens.sub.LongPressMenu
import ru.megboyzz.lks.profile.ui.theme.MainTheme
@Composable
@@ -60,14 +64,17 @@ fun ProfileCard(
shape = RoundedCornerShape(16.dp)
)
.defaultMinSize(minWidth = 240.dp)
.clip(RoundedCornerShape(16.dp))
.clickableWithNormalRipple(
onClick = { toggled =! toggled },
onLongClick = onLongPress
onClick = { toggled = !toggled },
onLongClick = onLongPress,
),
contentAlignment = Alignment.Center
) {
Column(
modifier = Modifier.fillMaxWidth().padding(12.dp),
modifier = Modifier
.fillMaxWidth()
.padding(12.dp),
horizontalAlignment = Alignment.CenterHorizontally,
verticalArrangement = Arrangement.spacedBy(8.dp)
) {
@@ -80,7 +87,9 @@ fun ProfileCard(
AnimatedVisibility(toggled) {
Column(
modifier = Modifier.padding(top = 4.dp).fillMaxWidth(),
modifier = Modifier
.padding(top = 4.dp)
.fillMaxWidth(),
verticalArrangement = Arrangement.spacedBy(12.dp),
horizontalAlignment = Alignment.CenterHorizontally
) {
@@ -166,4 +175,26 @@ private fun Main() {
}
}
}
@Composable
fun CardsColumn(
modifier: Modifier = Modifier,
lksStudents: List<LksStudent>,
onLongPress: (LksStudent) -> Unit
) {
Column(modifier) {
LazyColumn(
contentPadding = PaddingValues(12.dp),
verticalArrangement = Arrangement.spacedBy(12.dp)
) {
items(lksStudents) { student ->
ProfileCard(
lksStudent = student,
onLongPress = { onLongPress(student) }
)
}
}
}
}
@@ -0,0 +1,52 @@
package ru.megboyzz.lks.profile.ui.components
import androidx.compose.foundation.layout.Arrangement
import androidx.compose.foundation.layout.Box
import androidx.compose.foundation.layout.Column
import androidx.compose.foundation.layout.fillMaxSize
import androidx.compose.material.icons.Icons
import androidx.compose.material.icons.outlined.Info
import androidx.compose.material3.CircularProgressIndicator
import androidx.compose.material3.Icon
import androidx.compose.material3.Text
import androidx.compose.runtime.Composable
import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.unit.dp
@Composable
fun LoadingShield(title: String? = null) {
Box(
modifier = Modifier.fillMaxSize(),
contentAlignment = Alignment.Center
) {
Column(
verticalArrangement = Arrangement.spacedBy(16.dp),
horizontalAlignment = Alignment.CenterHorizontally
) {
CircularProgressIndicator()
if(title != null)
Text(title)
}
}
}
@Composable
fun ErrorShield(title: String? = null) {
Box(
modifier = Modifier.fillMaxSize(),
contentAlignment = Alignment.Center
) {
Column(
verticalArrangement = Arrangement.spacedBy(16.dp),
horizontalAlignment = Alignment.CenterHorizontally
) {
Icon(
imageVector = Icons.Outlined.Info,
contentDescription = null
)
if(title != null)
Text(title)
}
}
}
@@ -37,14 +37,19 @@ class SignInScreenModel @AssistedInject constructor(
val state = MutableStateFlow<SignInState>(SignInState.Idle)
private val _loadingScreen = MutableStateFlow(false)
val loadingScreen = _loadingScreen.asStateFlow()
private var cookie: Map<String, String> = mapOf()
init {
screenModelScope.launch {
screenModelScope.launch(Dispatchers.IO) {
_loadingScreen.emit(true)
cookie = lksRepository.restoreCooke()
if(lksRepository.cookiesIsValid(cookie))
navigator.push(SearchScreen())
_loadingScreen.emit(false)
}
state.onEach {
@@ -1,8 +1,10 @@
package ru.megboyzz.lks.profile.ui.screens
import androidx.compose.foundation.layout.Arrangement
import androidx.compose.foundation.layout.Box
import androidx.compose.foundation.layout.Column
import androidx.compose.foundation.layout.PaddingValues
import androidx.compose.foundation.layout.fillMaxSize
import androidx.compose.foundation.layout.padding
import androidx.compose.foundation.lazy.LazyColumn
import androidx.compose.foundation.lazy.items
@@ -11,12 +13,16 @@ import androidx.compose.material3.Text
import androidx.compose.runtime.Composable
import androidx.compose.runtime.collectAsState
import androidx.compose.runtime.getValue
import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.input.pointer.PointerIcon.Companion.Text
import androidx.compose.ui.unit.dp
import cafe.adriel.voyager.core.screen.Screen
import cafe.adriel.voyager.hilt.getScreenModel
import cafe.adriel.voyager.navigator.bottomSheet.LocalBottomSheetNavigator
import ru.megboyzz.lks.profile.ui.components.CardsColumn
import ru.megboyzz.lks.profile.ui.components.ErrorShield
import ru.megboyzz.lks.profile.ui.components.LoadingShield
import ru.megboyzz.lks.profile.ui.components.MainScaffold
import ru.megboyzz.lks.profile.ui.components.ProfileCard
import ru.megboyzz.lks.profile.ui.model.SearchScreenModel
@@ -39,28 +45,15 @@ class SearchScreen : Screen {
onFloatingButtonClick = { bottomSheetNavigator.show(SearchBottomScreen(screenModel)) }
) {
Column (
modifier = Modifier.padding(it)
) {
LazyColumn(
contentPadding = PaddingValues(8.dp),
verticalArrangement = Arrangement.spacedBy(4.dp)
) {
item {
when(state) {
is SearchScreenModel.UiState.Loading -> CircularProgressIndicator()
is SearchScreenModel.UiState.Error -> Text(state.status ?: "Ошибка")
SearchScreenModel.UiState.Idle -> { Text("Idle") }
}
}
items(list.students) {
ProfileCard(
lksStudent = it,
onLongPress = { bottomSheetNavigator.show(LongPressMenu(it)) }
)
}
when (state) {
is SearchScreenModel.UiState.Loading -> LoadingShield("Загрузка челиков")
is SearchScreenModel.UiState.Error -> ErrorShield(state.status)
else -> {
CardsColumn(
modifier = Modifier.padding(it),
lksStudents = list.students,
onLongPress = { student -> bottomSheetNavigator.show(LongPressMenu(student)) }
)
}
}
@@ -17,6 +17,7 @@ import androidx.compose.ui.unit.dp
import cafe.adriel.voyager.core.screen.Screen
import cafe.adriel.voyager.hilt.getScreenModel
import cafe.adriel.voyager.navigator.LocalNavigator
import ru.megboyzz.lks.profile.ui.components.LoadingShield
import ru.megboyzz.lks.profile.ui.model.SignInScreenModel
class SignInScreen : Screen {
@@ -35,6 +36,8 @@ class SignInScreen : Screen {
val state by viewModel.state.collectAsState()
val loading by viewModel.loadingScreen.collectAsState()
Box(
modifier = Modifier.fillMaxSize(),
contentAlignment = Alignment.Center
@@ -44,27 +47,33 @@ class SignInScreen : Screen {
horizontalAlignment = Alignment.CenterHorizontally
) {
OutlinedTextField(
value = username,
onValueChange = { viewModel.setUsername(it) }
)
if(loading){
LoadingShield("Проверка твоих куки файлов :-)")
} else {
OutlinedTextField(
value = password,
onValueChange = { viewModel.setPassword(it) }
)
OutlinedTextField(
value = username,
onValueChange = { viewModel.setUsername(it) }
)
OutlinedButton(
onClick = viewModel::signIn
) {
Text("Войти")
}
OutlinedTextField(
value = password,
onValueChange = { viewModel.setPassword(it) }
)
when(state) {
is SignInScreenModel.SignInState.Idle -> Text("")
is SignInScreenModel.SignInState.Success -> Text(state.status ?: "")
is SignInScreenModel.SignInState.Loading -> CircularProgressIndicator()
is SignInScreenModel.SignInState.Error -> Text(state.status ?: "Ошибка")
OutlinedButton(
onClick = viewModel::signIn
) {
Text("Войти")
}
when (state) {
is SignInScreenModel.SignInState.Idle -> Text("")
is SignInScreenModel.SignInState.Success -> Text(state.status ?: "")
is SignInScreenModel.SignInState.Loading -> CircularProgressIndicator()
is SignInScreenModel.SignInState.Error -> Text(state.status ?: "Ошибка")
else -> {}
}
}
}
@@ -21,9 +21,9 @@ class LongPressMenu(private val lksStudent: LksStudent) : Screen {
lksStudent = lksStudent
) {
Toast.makeText(context, "Переход на VK", Toast.LENGTH_SHORT).show()
val browserIntent = Intent(Intent.ACTION_VIEW, Uri.parse("https://vk.com/search?q=${lksStudent.studentFullName}"))
val browserIntent = Intent(Intent.ACTION_VIEW, Uri.parse("https://vk.com/search?q=${lksStudent.studentFullName?.split(" ")?.dropLast(1)?.joinToString(" ")}"))
browserIntent.`package` = "com.vkontakte.android"
context.startActivity(browserIntent);
context.startActivity(browserIntent)
}
+3 -1
View File
@@ -1,4 +1,5 @@
<vector xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:width="48dp"
android:height="48dp"
android:viewportWidth="48"
@@ -8,5 +9,6 @@
android:fillColor="#1976d2"/>
<path
android:pathData="M35.937,18.041c0.046,-0.151 0.068,-0.291 0.062,-0.416C35.984,17.263 35.735,17 35.149,17h-2.618c-0.661,0 -0.966,0.4 -1.144,0.801c0,0 -1.632,3.359 -3.513,5.574c-0.61,0.641 -0.92,0.625 -1.25,0.625C26.447,24 26,23.786 26,23.199v-5.185C26,17.32 25.827,17 25.268,17h-4.649C20.212,17 20,17.32 20,17.641c0,0.667 0.898,0.827 1,2.696v3.623C21,24.84 20.847,25 20.517,25c-0.89,0 -2.642,-3 -3.815,-6.932C16.448,17.294 16.194,17 15.533,17h-2.643C12.127,17 12,17.374 12,17.774c0,0.721 0.6,4.619 3.875,9.101C18.25,30.125 21.379,32 24.149,32c1.678,0 1.85,-0.427 1.85,-1.094v-2.972C26,27.133 26.183,27 26.717,27c0.381,0 1.158,0.25 2.658,2c1.73,2.018 2.044,3 3.036,3h2.618c0.608,0 0.957,-0.255 0.971,-0.75c0.003,-0.126 -0.015,-0.267 -0.056,-0.424c-0.194,-0.576 -1.084,-1.984 -2.194,-3.326c-0.615,-0.743 -1.222,-1.479 -1.501,-1.879C32.062,25.36 31.991,25.176 32,25c0.009,-0.185 0.105,-0.361 0.249,-0.607C32.223,24.393 35.607,19.642 35.937,18.041z"
android:fillColor="#fff"/>
android:fillColor="#fff"
tools:ignore="VectorPath" />
</vector>