Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 2 additions & 2 deletions MC1/Resources/Generated/L10n.swift
Original file line number Diff line number Diff line change
Expand Up @@ -2958,7 +2958,7 @@ public enum L10n {
}
public enum Error {
/// Location: ConnectionUIState.presentPairingFailure(_:) - Pairing failure alert messages
public static let authenticationFailed = L10n.tr("Onboarding", "deviceScan.error.authenticationFailed", fallback: "Couldn't pair the device. Check the PIN, then remove the device and try again.")
public static let authenticationFailed = L10n.tr("Onboarding", "deviceScan.error.authenticationFailed", fallback: "The saved pairing with this radio stopped working. Tap Remove and Try Again to re-pair in the app; the radio may show a new pairing code.")
/// Couldn't connect to the device. Try again, or remove it if the problem continues.
public static let connectionFailed = L10n.tr("Onboarding", "deviceScan.error.connectionFailed", fallback: "Couldn't connect to the device. Try again, or remove it if the problem continues.")
/// The PIN wasn't accepted. Check the PIN shown on your device, then try again. iOS will ask you to confirm removing the failed pairing first.
Expand Down Expand Up @@ -4785,7 +4785,7 @@ public enum L10n {
/// Button to export debug logs
public static let exportLogs = L10n.tr("Settings", "diagnostics.exportLogs", fallback: "Export Debug Logs")
/// Footer explaining log export
public static let footer = L10n.tr("Settings", "diagnostics.footer", fallback: "Export includes debug logs from the last 24 hours across app sessions. Logs are stored locally and automatically pruned.")
public static let footer = L10n.tr("Settings", "diagnostics.footer", fallback: "Export includes debug logs from all app sessions. Logs are stored locally and automatically removed after 7 days.")
/// Section header for diagnostics
public static let header = L10n.tr("Settings", "diagnostics.header", fallback: "Diagnostics")
public enum Alert {
Expand Down
2 changes: 1 addition & 1 deletion MC1/Resources/Localization/de.lproj/Onboarding.strings
Original file line number Diff line number Diff line change
Expand Up @@ -106,7 +106,7 @@
"deviceScan.demoModeAlert.message" = "Du kannst jetzt ohne Gerät fortfahren. Schalte den Demo-Modus jederzeit in den Einstellungen um.";

/* Location: ConnectionUIState.presentPairingFailure(_:) - Pairing failure alert messages */
"deviceScan.error.authenticationFailed" = "Gerät konnte nicht gekoppelt werden. Überprüfe die PIN, entferne dann das Gerät und versuche es erneut.";
"deviceScan.error.authenticationFailed" = "Die gespeicherte Kopplung mit diesem Funkgerät funktioniert nicht mehr. Tippe auf „Entfernen und erneut versuchen“, um es in der App neu zu koppeln; das Funkgerät zeigt möglicherweise einen neuen Kopplungscode an.";
"deviceScan.error.pinRejected" = "Die PIN wurde nicht akzeptiert. Überprüfe die auf deinem Gerät angezeigte PIN und versuche es erneut. iOS fragt dich zuerst, ob die fehlgeschlagene Kopplung entfernt werden soll.";
"deviceScan.error.connectionFailed" = "Verbindung zum Gerät fehlgeschlagen. Versuche es erneut, oder entferne das Gerät, wenn das Problem weiterhin besteht.";

Expand Down
2 changes: 1 addition & 1 deletion MC1/Resources/Localization/de.lproj/Settings.strings
Original file line number Diff line number Diff line change
Expand Up @@ -674,7 +674,7 @@
"diagnostics.clearLogs" = "Debug-Protokolle löschen";

/* Footer explaining log export */
"diagnostics.footer" = "Export enthält Debug-Protokolle der letzten 24 Stunden aus allen App-Sitzungen. Protokolle werden lokal gespeichert und automatisch bereinigt.";
"diagnostics.footer" = "Export enthält Debug-Protokolle aus allen App-Sitzungen. Protokolle werden lokal gespeichert und nach 7 Tagen automatisch entfernt.";

/* Alert title for clear logs confirmation */
"diagnostics.alert.clear.title" = "Debug-Protokolle löschen";
Expand Down
2 changes: 1 addition & 1 deletion MC1/Resources/Localization/en.lproj/Onboarding.strings
Original file line number Diff line number Diff line change
Expand Up @@ -106,7 +106,7 @@
"deviceScan.demoModeAlert.message" = "You can now continue without a device. Toggle demo mode in Settings anytime.";

/* Location: ConnectionUIState.presentPairingFailure(_:) - Pairing failure alert messages */
"deviceScan.error.authenticationFailed" = "Couldn't pair the device. Check the PIN, then remove the device and try again.";
"deviceScan.error.authenticationFailed" = "The saved pairing with this radio stopped working. Tap Remove and Try Again to re-pair in the app; the radio may show a new pairing code.";
"deviceScan.error.pinRejected" = "The PIN wasn't accepted. Check the PIN shown on your device, then try again. iOS will ask you to confirm removing the failed pairing first.";
"deviceScan.error.connectionFailed" = "Couldn't connect to the device. Try again, or remove it if the problem continues.";

Expand Down
2 changes: 1 addition & 1 deletion MC1/Resources/Localization/en.lproj/Settings.strings
Original file line number Diff line number Diff line change
Expand Up @@ -673,7 +673,7 @@
"diagnostics.clearLogs" = "Clear Debug Logs";

/* Footer explaining log export */
"diagnostics.footer" = "Export includes debug logs from the last 24 hours across app sessions. Logs are stored locally and automatically pruned.";
"diagnostics.footer" = "Export includes debug logs from all app sessions. Logs are stored locally and automatically removed after 7 days.";

/* Alert title for clear logs confirmation */
"diagnostics.alert.clear.title" = "Clear Debug Logs";
Expand Down
2 changes: 1 addition & 1 deletion MC1/Resources/Localization/es.lproj/Onboarding.strings
Original file line number Diff line number Diff line change
Expand Up @@ -106,7 +106,7 @@
"deviceScan.demoModeAlert.message" = "Ahora puedes continuar sin un dispositivo. Activa o desactiva el modo demo en Ajustes en cualquier momento.";

/* Location: ConnectionUIState.presentPairingFailure(_:) - Pairing failure alert messages */
"deviceScan.error.authenticationFailed" = "No se pudo enlazar el dispositivo. Comprueba el PIN, luego elimina el dispositivo e inténtalo de nuevo.";
"deviceScan.error.authenticationFailed" = "El enlace guardado con esta radio dejó de funcionar. Toca «Eliminar y reintentar» para volver a enlazarla en la app; la radio puede mostrar un nuevo código de enlace.";
"deviceScan.error.pinRejected" = "No se aceptó el PIN. Comprueba el PIN que se muestra en tu dispositivo e inténtalo de nuevo. Primero, iOS te pedirá que confirmes la eliminación del enlace fallido.";
"deviceScan.error.connectionFailed" = "No se pudo conectar al dispositivo. Inténtalo de nuevo, o elimínalo si el problema persiste.";

Expand Down
2 changes: 1 addition & 1 deletion MC1/Resources/Localization/es.lproj/Settings.strings
Original file line number Diff line number Diff line change
Expand Up @@ -674,7 +674,7 @@
"diagnostics.clearLogs" = "Borrar registros de depuración";

/* Footer explaining log export */
"diagnostics.footer" = "La exportación incluye registros de depuración de las últimas 24 horas de todas las sesiones de la app. Los registros se almacenan localmente y se eliminan automáticamente.";
"diagnostics.footer" = "La exportación incluye registros de depuración de todas las sesiones de la app. Los registros se almacenan localmente y se eliminan automáticamente después de 7 días.";

/* Alert title for clear logs confirmation */
"diagnostics.alert.clear.title" = "Borrar registros de depuración";
Expand Down
2 changes: 1 addition & 1 deletion MC1/Resources/Localization/fr.lproj/Onboarding.strings
Original file line number Diff line number Diff line change
Expand Up @@ -106,7 +106,7 @@
"deviceScan.demoModeAlert.message" = "Vous pouvez maintenant continuer sans appareil. Activez ou désactivez le mode démo dans les Réglages à tout moment.";

/* Location: ConnectionUIState.presentPairingFailure(_:) - Pairing failure alert messages */
"deviceScan.error.authenticationFailed" = "Impossible de jumeler l'appareil. Vérifiez le code PIN, puis supprimez l'appareil et réessayez.";
"deviceScan.error.authenticationFailed" = "Le jumelage enregistré avec cette radio ne fonctionne plus. Touchez « Supprimer et réessayer » pour la jumeler à nouveau dans l'app ; la radio peut afficher un nouveau code de jumelage.";
"deviceScan.error.pinRejected" = "Le code PIN n'a pas été accepté. Vérifiez le code PIN affiché sur votre appareil, puis réessayez. iOS vous demandera d'abord de confirmer la suppression du jumelage échoué.";
"deviceScan.error.connectionFailed" = "Impossible de se connecter à l'appareil. Réessayez, ou supprimez-le si le problème persiste.";

Expand Down
2 changes: 1 addition & 1 deletion MC1/Resources/Localization/fr.lproj/Settings.strings
Original file line number Diff line number Diff line change
Expand Up @@ -674,7 +674,7 @@
"diagnostics.clearLogs" = "Effacer les journaux de débogage";

/* Footer explaining log export */
"diagnostics.footer" = "L'exportation inclut les journaux de débogage des dernières 24 heures sur toutes les sessions de l'application. Les journaux sont stockés localement et automatiquement purgés.";
"diagnostics.footer" = "L'exportation inclut les journaux de débogage de toutes les sessions de l'application. Les journaux sont stockés localement et automatiquement supprimés après 7 jours.";

/* Alert title for clear logs confirmation */
"diagnostics.alert.clear.title" = "Effacer les journaux de débogage";
Expand Down
2 changes: 1 addition & 1 deletion MC1/Resources/Localization/nl.lproj/Onboarding.strings
Original file line number Diff line number Diff line change
Expand Up @@ -106,7 +106,7 @@
"deviceScan.demoModeAlert.message" = "Je kunt nu doorgaan zonder apparaat. Schakel demomodus op elk moment uit via Instellingen.";

/* Location: ConnectionUIState.presentPairingFailure(_:) - Pairing failure alert messages */
"deviceScan.error.authenticationFailed" = "Kan apparaat niet koppelen. Controleer de pincode, verwijder vervolgens het apparaat en probeer het opnieuw.";
"deviceScan.error.authenticationFailed" = "De opgeslagen koppeling met deze radio werkt niet meer. Tik op 'Verwijderen en opnieuw proberen' om opnieuw te koppelen in de app; de radio kan een nieuwe koppelcode tonen.";
"deviceScan.error.pinRejected" = "De pincode is niet geaccepteerd. Controleer de pincode die op je apparaat wordt weergegeven en probeer het opnieuw. iOS vraagt je eerst om te bevestigen dat de mislukte koppeling wordt verwijderd.";
"deviceScan.error.connectionFailed" = "Kan geen verbinding maken met het apparaat. Probeer het opnieuw, of verwijder het als het probleem aanhoudt.";

Expand Down
2 changes: 1 addition & 1 deletion MC1/Resources/Localization/nl.lproj/Settings.strings
Original file line number Diff line number Diff line change
Expand Up @@ -674,7 +674,7 @@
"diagnostics.clearLogs" = "Debuglogboeken wissen";

/* Footer explaining log export */
"diagnostics.footer" = "Export bevat debuglogboeken van de afgelopen 24 uur over app-sessies. Logboeken worden lokaal opgeslagen en automatisch opgeschoond.";
"diagnostics.footer" = "Export bevat debuglogboeken van alle app-sessies. Logboeken worden lokaal opgeslagen en na 7 dagen automatisch verwijderd.";

/* Alert title for clear logs confirmation */
"diagnostics.alert.clear.title" = "Debuglogboeken wissen";
Expand Down
2 changes: 1 addition & 1 deletion MC1/Resources/Localization/pl.lproj/Onboarding.strings
Original file line number Diff line number Diff line change
Expand Up @@ -106,7 +106,7 @@
"deviceScan.demoModeAlert.message" = "Możesz teraz kontynuować bez urządzenia. Wyłącz tryb demo w dowolnym momencie w Ustawieniach.";

/* Location: ConnectionUIState.presentPairingFailure(_:) - Pairing failure alert messages */
"deviceScan.error.authenticationFailed" = "Nie udało się sparować urządzenia. Sprawdź PIN, następnie usuń urządzenie i spróbuj ponownie.";
"deviceScan.error.authenticationFailed" = "Zapisane sparowanie z tym radiem przestało działać. Stuknij „Usuń i spróbuj ponownie”, aby sparować je ponownie w aplikacji; radio może wyświetlić nowy kod parowania.";
"deviceScan.error.pinRejected" = "PIN nie został zaakceptowany. Sprawdź PIN wyświetlany na urządzeniu i spróbuj ponownie. iOS najpierw poprosi o potwierdzenie usunięcia nieudanego parowania.";
"deviceScan.error.connectionFailed" = "Nie można połączyć się z urządzeniem. Spróbuj ponownie lub usuń je, jeśli problem nie ustępuje.";

Expand Down
2 changes: 1 addition & 1 deletion MC1/Resources/Localization/pl.lproj/Settings.strings
Original file line number Diff line number Diff line change
Expand Up @@ -674,7 +674,7 @@
"diagnostics.clearLogs" = "Wyczyść logi debugowania";

/* Footer explaining log export */
"diagnostics.footer" = "Eksport zawiera logi debugowania z ostatnich 24 godzin ze wszystkich sesji aplikacji. Logi są przechowywane lokalnie i automatycznie czyszczone.";
"diagnostics.footer" = "Eksport zawiera logi debugowania ze wszystkich sesji aplikacji. Logi są przechowywane lokalnie i automatycznie usuwane po 7 dniach.";

/* Alert title for clear logs confirmation */
"diagnostics.alert.clear.title" = "Wyczyść logi debugowania";
Expand Down
2 changes: 1 addition & 1 deletion MC1/Resources/Localization/ru.lproj/Onboarding.strings
Original file line number Diff line number Diff line change
Expand Up @@ -106,7 +106,7 @@
"deviceScan.demoModeAlert.message" = "Теперь вы можете продолжить без устройства. Отключите демо-режим в любое время в Настройках.";

/* Location: ConnectionUIState.presentPairingFailure(_:) - Pairing failure alert messages */
"deviceScan.error.authenticationFailed" = "Не удалось выполнить сопряжение с устройством. Проверьте PIN-код, затем удалите устройство и повторите попытку.";
"deviceScan.error.authenticationFailed" = "Сохранённое сопряжение с этой рацией перестало работать. Нажмите «Удалить и попробовать снова», чтобы выполнить сопряжение заново в приложении; рация может показать новый код сопряжения.";
"deviceScan.error.pinRejected" = "PIN-код не принят. Проверьте PIN-код, показанный на устройстве, и повторите попытку. Сначала iOS попросит подтвердить удаление неудачного сопряжения.";
"deviceScan.error.connectionFailed" = "Не удалось подключиться к устройству. Попробуйте снова или удалите его, если проблема сохраняется.";

Expand Down
2 changes: 1 addition & 1 deletion MC1/Resources/Localization/ru.lproj/Settings.strings
Original file line number Diff line number Diff line change
Expand Up @@ -674,7 +674,7 @@
"diagnostics.clearLogs" = "Очистить отладочные логи";

/* Footer explaining log export */
"diagnostics.footer" = "Экспорт включает отладочные логи за последние 24 часа по всем сессиям приложения. Логи хранятся локально и автоматически очищаются.";
"diagnostics.footer" = "Экспорт включает отладочные логи по всем сессиям приложения. Логи хранятся локально и автоматически удаляются через 7 дней.";

/* Alert title for clear logs confirmation */
"diagnostics.alert.clear.title" = "Очистить отладочные логи";
Expand Down
2 changes: 1 addition & 1 deletion MC1/Resources/Localization/uk.lproj/Onboarding.strings
Original file line number Diff line number Diff line change
Expand Up @@ -106,7 +106,7 @@
"deviceScan.demoModeAlert.message" = "Тепер ви можете продовжити без пристрою. Вимкніть демо-режим у будь-який час у Налаштуваннях.";

/* Location: ConnectionUIState.presentPairingFailure(_:) - Pairing failure alert messages */
"deviceScan.error.authenticationFailed" = "Не вдалося спарувати пристрій. Перевірте PIN-код, потім видаліть пристрій і спробуйте ще раз.";
"deviceScan.error.authenticationFailed" = "Збережене спарування з цією рацією перестало працювати. Натисніть «Видалити та спробувати знову», щоб спарувати її заново в застосунку; рація може показати новий код спарування.";
"deviceScan.error.pinRejected" = "PIN-код не прийнято. Перевірте PIN-код, показаний на пристрої, і спробуйте ще раз. Спочатку iOS попросить підтвердити видалення невдалого спарювання.";
"deviceScan.error.connectionFailed" = "Не вдалося підключитися до пристрою. Спробуйте знову або видаліть пристрій, якщо проблема не зникає.";

Expand Down
2 changes: 1 addition & 1 deletion MC1/Resources/Localization/uk.lproj/Settings.strings
Original file line number Diff line number Diff line change
Expand Up @@ -674,7 +674,7 @@
"diagnostics.clearLogs" = "Очистити журнали налагодження";

/* Footer explaining log export */
"diagnostics.footer" = "Експорт включає журнали налагодження за останні 24 години по всіх сесіях застосунку. Журнали зберігаються локально та автоматично очищаються.";
"diagnostics.footer" = "Експорт включає журнали налагодження по всіх сесіях застосунку. Журнали зберігаються локально та автоматично видаляються через 7 днів.";

/* Alert title for clear logs confirmation */
"diagnostics.alert.clear.title" = "Очистити журнали налагодження";
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -104,7 +104,7 @@
"deviceScan.demoModeAlert.message" = "您现在可以无需设备继续。随时在设置中切换演示模式。";

/* Location: ConnectionUIState.presentPairingFailure(_:) - Pairing failure alert messages */
"deviceScan.error.authenticationFailed" = "无法配对设备。请检查 PIN 码,然后移除设备并重试。";
"deviceScan.error.authenticationFailed" = "与此电台保存的配对已失效。点按“移除并重试”在应用内重新配对;电台可能会显示新的配对码。";
"deviceScan.error.pinRejected" = "PIN 码未被接受。请检查设备上显示的 PIN 码,然后重试。iOS 会先要求你确认移除失败的配对。";
"deviceScan.error.connectionFailed" = "无法连接到设备。请重试,或在问题持续时移除设备。";

Expand Down
2 changes: 1 addition & 1 deletion MC1/Resources/Localization/zh-Hans.lproj/Settings.strings
Original file line number Diff line number Diff line change
Expand Up @@ -660,7 +660,7 @@
"diagnostics.clearLogs" = "清除调试日志";

/* Footer explaining log export */
"diagnostics.footer" = "导出包括跨应用会话的最后 24 小时的调试日志。日志本地存储并自动清理。";
"diagnostics.footer" = "导出包括所有应用会话的调试日志。日志本地存储,并在 7 天后自动删除。";

/* Alert title for clear logs confirmation */
"diagnostics.alert.clear.title" = "清除调试日志";
Expand Down
9 changes: 4 additions & 5 deletions MC1/Services/LogExportService.swift
Original file line number Diff line number Diff line change
Expand Up @@ -159,14 +159,13 @@ enum LogExportService {
}

private static func generateLogsSection(persistenceStore: PersistenceStore) async -> String {
var lines = ["=== Logs (Last 24 Hours) ==="]
var lines = ["=== Logs (Last 7 Days) ==="]

do {
let secondsPerDay: TimeInterval = 86400
let twentyFourHoursAgo = Date().addingTimeInterval(-secondsPerDay)
let retentionStart = Date().addingTimeInterval(-DebugLogRetention.window)
let entries = try await persistenceStore.fetchDebugLogEntries(
since: twentyFourHoursAgo,
limit: 1000
since: retentionStart,
limit: DebugLogRetention.maxEntries
)

if entries.isEmpty {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -534,6 +534,10 @@ extension ConnectionManager {

let (meshCoreSelfInfo, deviceCapabilities) = try await initializeSession(newSession)

// Session traffic flowed over the encrypted UART link, so the bond is
// proven healthy as of now.
recordBondVerification(deviceID: deviceID)

// Configure BLE write pacing based on device platform
await configureBLEPacing(for: deviceCapabilities)

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -93,6 +93,10 @@ extension ConnectionManager: BLEReconnectionDelegate {
throw error
}

// Session traffic flowed over the encrypted UART link, so the bond is
// proven healthy as of now.
recordBondVerification(deviceID: deviceID)

// Check after await — user may have disconnected or a new reconnect cycle may have started
guard connectionIntent.wantsConnection else {
logger.info("User disconnected during session setup")
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -763,6 +763,10 @@ public extension ConnectionManager {

let (meshCoreSelfInfo, deviceCapabilities) = try await initializeSession(newSession)

// Session traffic flowed over the encrypted UART link, so the bond is
// proven healthy as of now.
recordBondVerification(deviceID: deviceID)

// Configure BLE write pacing based on device platform
await configureBLEPacing(for: deviceCapabilities)

Expand Down
Loading
Loading