fix login and add notifications
This commit is contained in:
@@ -569,7 +569,7 @@ Future<AuthInterceptor> authInterceptor(Ref ref, Dio dio) async {
|
||||
@riverpod
|
||||
LoggingInterceptor loggingInterceptor(Ref ref) {
|
||||
// Only enable logging in debug mode
|
||||
const bool isDebug = true; // TODO: Replace with kDebugMode from Flutter
|
||||
const bool isDebug = false; // TODO: Replace with kDebugMode from Flutter
|
||||
|
||||
return LoggingInterceptor(
|
||||
enableRequestLogging: false,
|
||||
|
||||
@@ -65,14 +65,21 @@ final routerProvider = Provider<GoRouter>((ref) {
|
||||
redirect: (context, state) {
|
||||
final isLoading = authState.isLoading;
|
||||
final isLoggedIn = authState.value != null;
|
||||
final isOnSplashPage = state.matchedLocation == RouteNames.splash;
|
||||
final isOnLoginPage = state.matchedLocation == RouteNames.login;
|
||||
final isOnForgotPasswordPage =
|
||||
state.matchedLocation == RouteNames.forgotPassword;
|
||||
final isOnRegisterPage = state.matchedLocation == RouteNames.register;
|
||||
final isOnBusinessUnitPage =
|
||||
state.matchedLocation == RouteNames.businessUnitSelection;
|
||||
final isOnOtpPage = state.matchedLocation == RouteNames.otpVerification;
|
||||
final currentPath = state.matchedLocation;
|
||||
final targetPath = state.uri.toString();
|
||||
|
||||
// Log redirect attempts for debugging
|
||||
print('🔄 Router redirect check:');
|
||||
print(' Current: $currentPath');
|
||||
print(' Target: $targetPath');
|
||||
print(' isLoading: $isLoading, isLoggedIn: $isLoggedIn');
|
||||
|
||||
final isOnSplashPage = currentPath == RouteNames.splash;
|
||||
final isOnLoginPage = currentPath == RouteNames.login;
|
||||
final isOnForgotPasswordPage = currentPath == RouteNames.forgotPassword;
|
||||
final isOnRegisterPage = currentPath == RouteNames.register;
|
||||
final isOnBusinessUnitPage = currentPath == RouteNames.businessUnitSelection;
|
||||
final isOnOtpPage = currentPath == RouteNames.otpVerification;
|
||||
final isOnAuthPage =
|
||||
isOnLoginPage ||
|
||||
isOnForgotPasswordPage ||
|
||||
@@ -82,25 +89,35 @@ final routerProvider = Provider<GoRouter>((ref) {
|
||||
|
||||
// While loading auth state, show splash screen
|
||||
if (isLoading) {
|
||||
return RouteNames.splash;
|
||||
if (!isOnSplashPage) {
|
||||
print(' ➡️ Redirecting to splash (loading)');
|
||||
return RouteNames.splash;
|
||||
}
|
||||
print(' ✓ Already on splash (loading)');
|
||||
return null;
|
||||
}
|
||||
|
||||
// After loading, redirect from splash to appropriate page
|
||||
if (isOnSplashPage && !isLoading) {
|
||||
return isLoggedIn ? RouteNames.home : RouteNames.login;
|
||||
if (isOnSplashPage) {
|
||||
final destination = isLoggedIn ? RouteNames.home : RouteNames.login;
|
||||
print(' ➡️ Redirecting from splash to $destination');
|
||||
return destination;
|
||||
}
|
||||
|
||||
// If not logged in and not on auth/splash pages, redirect to login
|
||||
if (!isLoggedIn && !isOnAuthPage && !isOnSplashPage) {
|
||||
if (!isLoggedIn && !isOnAuthPage) {
|
||||
print(' ➡️ Redirecting to login (not authenticated)');
|
||||
return RouteNames.login;
|
||||
}
|
||||
|
||||
// If logged in and on login page, redirect to home
|
||||
if (isLoggedIn && isOnLoginPage) {
|
||||
print(' ➡️ Redirecting to home (already logged in)');
|
||||
return RouteNames.home;
|
||||
}
|
||||
|
||||
// No redirect needed
|
||||
print(' ✓ No redirect needed');
|
||||
return null;
|
||||
},
|
||||
|
||||
@@ -549,7 +566,7 @@ final routerProvider = Provider<GoRouter>((ref) {
|
||||
),
|
||||
|
||||
// Debug logging (disable in production)
|
||||
debugLogDiagnostics: true,
|
||||
debugLogDiagnostics: false, // Using custom logs instead
|
||||
);
|
||||
});
|
||||
|
||||
|
||||
@@ -88,10 +88,8 @@ class Auth extends _$Auth {
|
||||
@override
|
||||
Future<User?> build() async {
|
||||
// Simple initialization - just check if user is logged in
|
||||
// Don't call getSession() here to avoid ref disposal issues
|
||||
// Do this ONCE on app startup and don't rebuild
|
||||
try {
|
||||
final secureStorage = ref.read(secureStorageProvider);
|
||||
|
||||
// Check if "Remember Me" was enabled
|
||||
final rememberMe = await _localDataSource.getRememberMe();
|
||||
|
||||
@@ -101,6 +99,7 @@ class Auth extends _$Auth {
|
||||
}
|
||||
|
||||
// Check if we have a stored session
|
||||
final secureStorage = ref.read(secureStorageProvider);
|
||||
final sid = await secureStorage.read(key: 'frappe_sid');
|
||||
final userId = await secureStorage.read(key: 'frappe_user_id');
|
||||
final fullName = await secureStorage.read(key: 'frappe_full_name');
|
||||
|
||||
@@ -4,6 +4,7 @@ import 'package:flutter/foundation.dart';
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter/services.dart';
|
||||
import 'package:flutter_riverpod/flutter_riverpod.dart';
|
||||
import 'package:onesignal_flutter/onesignal_flutter.dart';
|
||||
import 'package:shared_preferences/shared_preferences.dart';
|
||||
|
||||
import 'package:worker/app.dart';
|
||||
@@ -29,6 +30,10 @@ void main() async {
|
||||
|
||||
// Initialize app with error handling
|
||||
await _initializeApp();
|
||||
|
||||
// Enable verbose logging for debugging (remove in production)
|
||||
|
||||
|
||||
}
|
||||
|
||||
/// Initialize all app dependencies with comprehensive error handling
|
||||
@@ -40,6 +45,55 @@ Future<void> _initializeApp() async {
|
||||
// Initialize core dependencies in parallel for faster startup
|
||||
await Future.wait([_initializeHive(), _initializeSharedPreferences()]);
|
||||
|
||||
// Initialize OneSignal with verbose logging for debugging
|
||||
OneSignal.Debug.setLogLevel(OSLogLevel.verbose);
|
||||
|
||||
// Initialize with your OneSignal App ID
|
||||
OneSignal.initialize("778ca22d-c719-4ec8-86cb-a6b911166066");
|
||||
|
||||
debugPrint('🔔 OneSignal initialized');
|
||||
|
||||
// Add observer BEFORE requesting permission to catch the subscription event
|
||||
OneSignal.User.pushSubscription.addObserver((state) {
|
||||
debugPrint('🔔 Push subscription state changed:');
|
||||
debugPrint(' Previous - optedIn: ${state.previous.optedIn}, id: ${state.previous.id}');
|
||||
debugPrint(' Current - optedIn: ${state.current.optedIn}, id: ${state.current.id}');
|
||||
debugPrint(' Subscription ID: ${state.current.id}');
|
||||
debugPrint(' Push Token: ${state.current.token}');
|
||||
|
||||
// Save subscription info when available
|
||||
if (state.current.id != null) {
|
||||
debugPrint('🔔 ✅ Device successfully subscribed!');
|
||||
}
|
||||
});
|
||||
|
||||
// Add notification permission observer
|
||||
OneSignal.Notifications.addPermissionObserver((isGranted) {
|
||||
debugPrint('🔔 Notification permission changed: $isGranted');
|
||||
});
|
||||
|
||||
// Request permission - TRUE to show the native permission prompt
|
||||
final accepted = await OneSignal.Notifications.requestPermission(true);
|
||||
debugPrint('🔔 Permission request result: $accepted');
|
||||
|
||||
// Give OneSignal SDK time to complete initialization and server registration
|
||||
// This is necessary because the subscription happens asynchronously
|
||||
await Future.delayed(const Duration(seconds: 2));
|
||||
|
||||
// Check current subscription status after initialization completes
|
||||
final optedIn = OneSignal.User.pushSubscription.optedIn;
|
||||
final id = OneSignal.User.pushSubscription.id;
|
||||
final token = OneSignal.User.pushSubscription.token;
|
||||
|
||||
debugPrint('🔔 Current subscription status (after delay):');
|
||||
debugPrint(' Opted In: $optedIn');
|
||||
debugPrint(' Subscription ID: $id');
|
||||
debugPrint(' Push Token: $token');
|
||||
|
||||
if (id == null) {
|
||||
debugPrint('🔔 ⚠️ Subscription ID is still null - check device connectivity and OneSignal app ID');
|
||||
}
|
||||
|
||||
// Run the app with Riverpod ProviderScope
|
||||
runApp(const ProviderScope(child: WorkerApp()));
|
||||
} catch (error, stackTrace) {
|
||||
|
||||
Reference in New Issue
Block a user