diff --git a/PLAYSTORE_REVIEW.md b/PLAYSTORE_REVIEW.md new file mode 100644 index 0000000..765c5aa --- /dev/null +++ b/PLAYSTORE_REVIEW.md @@ -0,0 +1,32 @@ +# Google Play: Zugang für die App-Prüfung + +In der Play Console unter **Richtlinien und Programme → App-Inhalte → App-Zugriff / Anmeldedaten** angeben, dass einige Funktionen eine Anmeldung erfordern. Eine neue Anleitung mit Titel `Harheimer TC review account` anlegen. + +## Konto auf dem Backend der eingereichten App einrichten + +Nach Deployment dieser Änderungen im Projektverzeichnis des entsprechenden Servers ausführen: + +```bash +node scripts/setup-playstore-review.js +``` + +Das Skript liest die dortige `.env` einschließlich `ENCRYPTION_KEY`, sichert die bisherige Benutzerdatei und erstellt ein aktives, ausgeblendetes Mitgliedskonto. Standardadresse: `playstore-review@harheimertc.invalid`. Dies ist bewusst kein echtes Postfach. Das zufällig erzeugte Passwort wird einmal ausgegeben und muss sicher abgelegt werden. Bei erneutem Aufruf bleibt es unverändert. Optional können `PLAYSTORE_REVIEW_EMAIL` und `PLAYSTORE_REVIEW_PASSWORD` gesetzt werden; ein explizites Passwort aktualisiert das bestehende Review-Konto. Kein reguläres Konto wird umgewandelt. + +In der Play Console die ausgegebene E-Mail-Adresse und das Passwort eintragen. Zusätzliche Anweisungen auf Englisch: + +> Open the app and go to Login. Sign in with the email address and password provided above. This account is already activated and provides access to the member features. No registration, email verification, one-time code or approval is required. Please stay signed in while testing forms. Outgoing emails triggered by this account are suppressed by the server. When a form asks for an email address, use the review account email provided above, including when testing while signed out. + +Die Zugangsdaten dauerhaft gültig halten. Das Konto ist ein Mitglied, kein CMS-Administrator. + +## Versandsperre + +Alle SMTP-Versandstellen verwenden dieselbe serverseitige Sperre: + +- Für authentifizierte Konten mit `accountType: playstore_review` oder der konfigurierten `PLAYSTORE_REVIEW_EMAIL` wird kein SMTP-Versand ausgeführt, auch bei abweichender Formularadresse. +- Mails an die Review-Adresse sowie Kontaktmails mit dieser Antwortadresse werden auch ohne Anmeldung unterdrückt. Registrierung und Mitgliedsanträge prüfen zusätzlich die Formularadresse. Gemischte Empfängerlisten mit einem Review-Konto werden vollständig unterdrückt. +- `MAIL_DELIVERY_DISABLED=true` unterdrückt sämtliche SMTP-Mails einer Installation. Die PM2-Testkonfiguration setzt dies standardmäßig; Produktion bleibt ohne diese Einstellung aktiv. Nach Konfigurationsänderungen den Backend-Prozess mit aktualisierter Umgebung neu starten. +- `DEBUG=true` allein verhindert keinen Mailversand. + +Die Versandsperre ist keine isolierte Demo-Datenbank: Formulare können weiterhin Daten speichern und Push-Benachrichtigungen auslösen. Ohne Anmeldung und mit einer fremden Formularadresse lässt sich eine Anfrage keinem Review-Konto zuordnen. Für vollständig mailfreie Tests daher eine separate Testinstanz mit `MAIL_DELIVERY_DISABLED=true` verwenden und sicherstellen, dass der eingereichte App-Build dieses Backend nutzt. + +Google-Anforderungen: https://support.google.com/googleplay/android-developer/answer/15748846 diff --git a/android-app/app/src/main/java/de/harheimertc/ui/components/AppNavigationHeader.kt b/android-app/app/src/main/java/de/harheimertc/ui/components/AppNavigationHeader.kt index 9c76bb8..40c6780 100755 --- a/android-app/app/src/main/java/de/harheimertc/ui/components/AppNavigationHeader.kt +++ b/android-app/app/src/main/java/de/harheimertc/ui/components/AppNavigationHeader.kt @@ -80,8 +80,8 @@ private fun CompactNavigation( navigationState: NavigationUiState = NavigationUiState(), ) { val routeSection = menuSection(selectedRoute) - val sectionOverride = androidx.compose.runtime.remember { androidx.compose.runtime.mutableStateOf(null) } - val section = routeSection ?: sectionOverride.value + val sectionOverride = androidx.compose.runtime.remember(selectedRoute) { androidx.compose.runtime.mutableStateOf(null) } + val section = sectionOverride.value ?: routeSection val subItems = submenu(section, navigationState) val mainScroll = rememberScrollState() diff --git a/android-app/app/src/main/java/de/harheimertc/ui/navigation/NavGraph.kt b/android-app/app/src/main/java/de/harheimertc/ui/navigation/NavGraph.kt index 4d6f3e1..a618ba5 100755 --- a/android-app/app/src/main/java/de/harheimertc/ui/navigation/NavGraph.kt +++ b/android-app/app/src/main/java/de/harheimertc/ui/navigation/NavGraph.kt @@ -12,6 +12,7 @@ import androidx.compose.foundation.layout.Column import androidx.compose.foundation.layout.fillMaxSize import androidx.compose.foundation.layout.fillMaxWidth import androidx.compose.foundation.layout.padding +import androidx.compose.foundation.layout.systemBarsPadding import androidx.compose.ui.Alignment import androidx.compose.ui.Modifier import androidx.compose.ui.graphics.Color @@ -45,13 +46,13 @@ fun NavGraph( LaunchedEffect(currentRoute) { navigationViewModel.refreshSession() } - LaunchedEffect(currentRoute, navigationState.loggedIn) { - navigationViewModel.setLiveTickerActive( - navigationState.loggedIn && (currentRoute == "intern" || currentRoute?.startsWith("intern/") == true || currentRoute == "cms" || currentRoute?.startsWith("cms/") == true), - ) + LaunchedEffect(navigationState.loggedIn) { + navigationViewModel.setLiveTickerActive(navigationState.loggedIn) } - BoxWithConstraints(modifier = Modifier.fillMaxSize()) { - val persistentNavigation = maxWidth >= 600.dp + BoxWithConstraints(modifier = Modifier.fillMaxSize().systemBarsPadding()) { + val tabletNavigation = maxWidth >= 600.dp + // Signed-in phones share the same menu and ticker above every screen. + val persistentNavigation = tabletNavigation || navigationState.loggedIn Column(modifier = Modifier.fillMaxSize()) { navigationState.connectionNote?.let { message -> Surface(color = Color(0xFFFFF4E5), modifier = Modifier.fillMaxWidth()) { @@ -74,14 +75,16 @@ fun NavGraph( } } }, - webTabletNavigation = true, + webTabletNavigation = tabletNavigation, navigationState = navigationState, ) } - LiveTickerBanner( - matches = navigationState.liveTickerMatches, - loaded = navigationState.liveTickerLoaded, - ) + if (navigationState.loggedIn) { + LiveTickerBanner( + matches = navigationState.liveTickerMatches, + loaded = navigationState.liveTickerLoaded, + ) + } NavHost( navController = navController, startDestination = startDestination, diff --git a/android-app/gradle.properties b/android-app/gradle.properties index f29737d..27cfdc4 100755 --- a/android-app/gradle.properties +++ b/android-app/gradle.properties @@ -8,8 +8,8 @@ LOCAL_API_BASE_URL=https://harheimertc.tsschulz.de/ PRODUCTION_API_BASE_URL=https://harheimertc.de/ # Android app versioning for Play Store uploads -ANDROID_VERSION_CODE=39 -ANDROID_VERSION_NAME=0.11.1 +ANDROID_VERSION_CODE=40 +ANDROID_VERSION_NAME=0.11.2 # Temporary hotfix: disable R8 minification for release to avoid Retrofit generic signature stripping. RELEASE_MINIFY_ENABLED=false diff --git a/app.vue b/app.vue index 6493c6b..a0c43e1 100755 --- a/app.vue +++ b/app.vue @@ -1,8 +1,8 @@