/// Session Provider
///
/// Manages authentication session (SID and CSRF token)
library;

import 'package:curl_logger_dio_interceptor/curl_logger_dio_interceptor.dart';
import 'package:dio/dio.dart';
import 'package:riverpod_annotation/riverpod_annotation.dart';
import 'package:worker/core/constants/api_constants.dart';
import 'package:worker/features/auth/data/datasources/auth_remote_datasource.dart';

part 'session_provider.g.dart';

/// Provider for Dio instance
@Riverpod(keepAlive: true)
Dio dio(Ref ref) {
  final dio = Dio(
    BaseOptions(
      baseUrl: ApiConstants.baseUrl,
      connectTimeout: const Duration(seconds: 30),
      receiveTimeout: const Duration(seconds: 30),
    ),
  );

  // Add curl logger interceptor for debugging
  dio.interceptors.add(CurlLoggerDioInterceptor(printOnSuccess: true));

  return dio;
}

/// Provider for AuthRemoteDataSource
@Riverpod(keepAlive: true)
AuthRemoteDataSource authRemoteDataSource(Ref ref) {
  final dio = ref.watch(dioProvider);
  return AuthRemoteDataSource(dio);
}

/// Session State
class SessionState {
  final String? sid;
  final String? csrfToken;
  final bool isLoading;
  final String? error;

  const SessionState({
    this.sid,
    this.csrfToken,
    this.isLoading = false,
    this.error,
  });

  SessionState copyWith({
    String? sid,
    String? csrfToken,
    bool? isLoading,
    String? error,
  }) {
    return SessionState(
      sid: sid ?? this.sid,
      csrfToken: csrfToken ?? this.csrfToken,
      isLoading: isLoading ?? this.isLoading,
      error: error ?? this.error,
    );
  }

  bool get hasSession => sid != null && csrfToken != null;
}

/// Session Provider
///
/// Manages the authentication session including SID and CSRF token.
/// This should be called before making any authenticated requests.
/// keepAlive: true ensures the session persists across the app lifecycle.
@Riverpod(keepAlive: true)
class Session extends _$Session {
  @override
  SessionState build() {
    return const SessionState();
  }

  /// Get session from API
  Future<void> getSession() async {
    state = state.copyWith(isLoading: true, error: null);

    try {
      final dataSource = ref.read(authRemoteDataSourceProvider);
      final response = await dataSource.getSession();

      state = SessionState(
        sid: response.message.data.sid,
        csrfToken: response.message.data.csrfToken,
        isLoading: false,
      );
    } catch (e) {
      state = SessionState(
        isLoading: false,
        error: e.toString(),
      );
      rethrow;
    }
  }

  /// Clear session
  void clearSession() {
    state = const SessionState();
  }
}
